The XPath visitor class is now working

This commit is contained in:
John Wiegley 2007-05-15 05:44:06 +00:00
parent 7747a8f93b
commit d89f6e1c44
2 changed files with 26 additions and 29 deletions

View file

@ -46,10 +46,6 @@
#include <fdstream.hpp> #include <fdstream.hpp>
#endif #endif
void print_node(ledger::xml::node_t& node) {
node.print(std::cout);
}
static int read_and_report(ledger::report_t * report, int argc, char * argv[], static int read_and_report(ledger::report_t * report, int argc, char * argv[],
char * envp[]) char * envp[])
{ {
@ -269,25 +265,15 @@ static int read_and_report(ledger::report_t * report, int argc, char * argv[],
} }
else if (verb == "xpath") { else if (verb == "xpath") {
std::cout << "XPath parsed:" << std::endl; std::cout << "XPath parsed:" << std::endl;
xml::xpath_t xpath(*arg); xml::xpath_t xpath(*arg);
xpath.print(*out, xml_document); xpath.print(*out, xml_document);
*out << std::endl; *out << std::endl;
#if 1 foreach (xml::node_t * node, xpath.find_all(xml_document, report)) {
try { node->print(std::cout);
xml::xpath_t::path_t path_selection(xpath); std::cout << std::endl;
path_selection.visit(xml_document, report, bind(print_node, _1));
} }
catch (...) {
throw;
}
#else
value_t nodelist;
xpath.calc(nodelist, xml_document, report);
foreach (const value_t& node, nodelist.as_sequence())
node.as_xml_node()->print(*out);
#endif
return 0; return 0;
} }

View file

@ -272,7 +272,11 @@ public:
class path_iterator_t class path_iterator_t
{ {
path_t path; path_t path;
std::vector<node_t *> sequence; node_t& start;
scope_t * scope;
mutable std::vector<node_t *> sequence;
mutable bool searched;
struct node_appender_t { struct node_appender_t {
std::vector<node_t *>& sequence; std::vector<node_t *>& sequence;
@ -288,13 +292,21 @@ public:
typedef std::vector<node_t *>::const_iterator const_iterator; typedef std::vector<node_t *>::const_iterator const_iterator;
path_iterator_t(const xpath_t& path_expr, path_iterator_t(const xpath_t& path_expr,
node_t& start, scope_t * scope) node_t& _start, scope_t * _scope)
: path(path_expr) { : path(path_expr), start(_start), scope(_scope),
path.visit(start, scope, node_appender_t(sequence)); searched(false) {
} }
iterator begin() { return sequence.begin(); } iterator begin() {
const_iterator begin() const { return sequence.begin(); } if (! searched) {
path.visit(start, scope, node_appender_t(sequence));
searched = true;
}
return sequence.begin();
}
const_iterator begin() const {
return const_cast<path_iterator_t *>(this)->begin();
}
iterator end() { return sequence.end(); } iterator end() { return sequence.end(); }
const_iterator end() const { return sequence.end(); } const_iterator end() const { return sequence.end(); }
@ -748,6 +760,9 @@ public:
path_t path(*this); path_t path(*this);
path.find_all(result, start, scope); path.find_all(result, start, scope);
} }
path_iterator_t find_all(node_t& start, scope_t * scope) {
return path_iterator_t(*this, start, scope);
}
void visit(node_t& start, scope_t * scope, void visit(node_t& start, scope_t * scope,
const function<void (node_t&)>& func) { const function<void (node_t&)>& func) {
@ -755,10 +770,6 @@ public:
path.visit(start, scope, func); path.visit(start, scope, func);
} }
path_iterator_t sequence(node_t& start, scope_t * scope) {
return path_iterator_t(*this, start, scope);
}
void print(std::ostream& out, xml::document_t& document) const { void print(std::ostream& out, xml::document_t& document) const {
print(out, document, true, NULL, NULL, NULL); print(out, document, true, NULL, NULL, NULL);
} }