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
00035 #include "streamtracker.h"
00036
00037 StreamTracker::StreamTracker(ProjectionDFA * _pdfa, Buffer * _buffer):
00038 cur(_pdfa->getInitialState()), buffer(_buffer),
00039 tagmap(TagMap::getInstance()), skip_subtree_depth(0), keep_subtree_depth(0) {
00040 }
00041
00042 StreamTracker::~StreamTracker() {
00043 }
00044
00045 void StreamTracker::processOpeningTag(const char *_tag) {
00046
00047 if (skip_subtree_depth > 0) {
00048 skip_subtree_depth++;
00049 } else if (keep_subtree_depth > 0) {
00050 buffer->appendTag(tagmap->insertTagWithOffset(_tag, 1, 1));
00051 keep_subtree_depth++;
00052 } else {
00053 TAG tag = tagmap->insertTagWithOffset(_tag, 1, 1);
00054 short success = TRANSITION_UNKNOWN;
00055
00056 cur = cur->takeTransition(tag, success);
00057
00058 switch (success) {
00059 case TRANSITION_REGULAR:
00060 if (cur->keepNode()) {
00061 buffer->appendTag(tag, cur->getCumulativeRoles(),
00062 cur->getNonCumulativeRoles());
00063 }
00064 break;
00065
00066 case TRANSITION_SKIP_SUBTREE:
00067 skip_subtree_depth++;
00068 break;
00069
00070 case TRANSITION_KEEP_SUBTREE:
00071 buffer->appendTag(tag);
00072 keep_subtree_depth++;
00073 break;
00074 }
00075 }
00076 }
00077
00078 void StreamTracker::processBachelorTag(const char *_tag) {
00079
00080 if (skip_subtree_depth > 0) {
00081
00082 } else if (keep_subtree_depth > 0) {
00083 buffer->appendTag(tagmap->insertTagWithOffset(_tag, 1, 2));
00084 buffer->closeTag();
00085 } else {
00086
00087 TAG tag = tagmap->insertTagWithOffset(_tag, 1, 2);
00088 short success = TRANSITION_UNKNOWN;
00089
00090 cur = cur->takeTransition(tag, success);
00091
00092 switch (success) {
00093 case TRANSITION_REGULAR:
00094 if (cur->keepNode()) {
00095 buffer->appendTag(tag, cur->getCumulativeRoles(),
00096 cur->getNonCumulativeRoles());
00097 buffer->closeTag();
00098 }
00099 cur = cur->traceBack();
00100 break;
00101
00102 case TRANSITION_SKIP_SUBTREE:
00103 break;
00104
00105 case TRANSITION_KEEP_SUBTREE:
00106 buffer->appendTag(tag);
00107 buffer->closeTag();
00108 break;
00109 }
00110 }
00111 }
00112
00113 #ifdef VALIDATION
00114
00115
00116
00117 void StreamTracker::processClosingTag(const char *_tag) {
00118 if (skip_subtree_depth > 0) {
00119 skip_subtree_depth--;
00120 } else if (keep_subtree_depth > 0) {
00121 buffer->closeTag();
00122 keep_subtree_depth--;
00123 } else {
00124 TAG tag = TagMap::getInstance()->insertTagWithOffset(_tag, 2, 1);
00125
00126 if (cur->keepNode()) {
00127 if (buffer->getCurrent() &&
00128 buffer->getCurrent()->type == TYPE_TAG &&
00129 ((TagNode *) buffer->getCurrent()->node)->tag == tag) {
00130 buffer->closeTag();
00131 } else {
00132 throw ParseException("Not Well-Formed XML Document",
00133 eid_parse_xml);
00134 }
00135 }
00136 cur = cur->traceBack();
00137 }
00138 }
00139
00140 void StreamTracker::processClosingTag(TAG tag) {
00141 if (skip_subtree_depth > 0) {
00142 skip_subtree_depth--;
00143 } else if (keep_subtree_depth > 0) {
00144 buffer->closeTag();
00145 keep_subtree_depth--;
00146 } else {
00147 if (cur->keepNode()) {
00148 if (buffer->getCurrent()->type == TYPE_TAG &&
00149 ((TagNode *) buffer->getCurrent()->node)->tag == tag) {
00150 buffer->closeTag();
00151 } else {
00152 throw ParseException("Not Well-Formed XML Document",
00153 eid_parse_xml);
00154 }
00155 }
00156 cur = cur->traceBack();
00157 }
00158 }
00159 #else
00160 void StreamTracker::processClosingTag() {
00161 if (skip_subtree_depth > 0) {
00162 skip_subtree_depth--;
00163 } else if (keep_subtree_depth > 0) {
00164 buffer->closeTag();
00165 keep_subtree_depth--;
00166 } else {
00167 if (cur->keepNode()) {
00168 buffer->closeTag();
00169 }
00170 cur = cur->traceBack();
00171 }
00172 }
00173 #endif // #ifdef VALIDATION
00174
00175 void StreamTracker::processPCData(const char *data) {
00176
00177 if (keep_subtree_depth > 0) {
00178 buffer->appendPCData(data);
00179 } else if (skip_subtree_depth > 0) {
00180
00181 } else {
00182 ProjectionDFAState *text_state = cur->takeTextTransition();
00183
00184 if (text_state) {
00185 buffer->appendPCData(data, text_state->getCumulativeRoles(),
00186 text_state->getNonCumulativeRoles());
00187
00188 }
00189 }
00190 }