diff --git a/include/XPath/impl/xpath_expression.hpp b/include/XPath/impl/xpath_expression.hpp index 897dfe9c..389ed03f 100644 --- a/include/XPath/impl/xpath_expression.hpp +++ b/include/XPath/impl/xpath_expression.hpp @@ -48,30 +48,58 @@ public: XPathValue evaluate(const DOM::Node& context) const { - ExecutionContext executionContext; - return evaluate(context, executionContext); + return evaluate(context, StaticExecutionContext()); } // evaluate + virtual bool evaluateAsBool(const DOM::Node& context) const + { + return evaluateAsBool(context, StaticExecutionContext()); + } + virtual double evaluateAsNumber(const DOM::Node& context) const + { + return evaluateAsNumber(context, StaticExecutionContext()); + } + virtual string_type evaluateAsString(const DOM::Node& context) const + { + return evaluateAsString(context, StaticExecutionContext()); + } + virtual NodeSet evaluateAsNodeSet(const DOM::Node& context) const + { + return evaluateAsNodeSet(context, StaticExecutionContext()); + } - virtual bool evaluateAsBool(const DOM::Node& context) const { return evaluate(context).asBool(); } - virtual double evaluateAsNumber(const DOM::Node& context) const { return evaluate(context).asNumber(); } - virtual string_type evaluateAsString(const DOM::Node& context) const { return evaluate(context).asString(); } - virtual NodeSet evaluateAsNodeSet(const DOM::Node& context) const { return evaluate(context).asNodeSet(); } - - virtual XPathValue evaluate(const DOM::Node& context, + virtual XPathValue evaluate(const DOM::Node& context, const ExecutionContext& executionContext) const = 0; virtual bool evaluateAsBool(const DOM::Node& context, - const ExecutionContext& executionContext) const { return evaluate(context, executionContext).asBool(); } + const ExecutionContext& executionContext) const + { + return evaluate(context, executionContext).asBool(); + } virtual double evaluateAsNumber(const DOM::Node& context, - const ExecutionContext& executionContext) const { return evaluate(context, executionContext).asNumber(); } + const ExecutionContext& executionContext) const + { + return evaluate(context, executionContext).asNumber(); + } virtual string_type evaluateAsString(const DOM::Node& context, - const ExecutionContext& executionContext) const { return evaluate(context, executionContext).asString(); } + const ExecutionContext& executionContext) const + { + return evaluate(context, executionContext).asString(); + } virtual NodeSet evaluateAsNodeSet(const DOM::Node& context, - const ExecutionContext& executionContext) const { return evaluate(context, executionContext).asNodeSet(); } + const ExecutionContext& executionContext) const + { + return evaluate(context, executionContext).asNodeSet(); + } virtual void scan(impl::Expression_scanner& scanner) const { scanner.scan(this); } private: + static const ExecutionContext& StaticExecutionContext() + { + static ExecutionContext executionContext; + return executionContext; + } // StaticExecutionContext + XPathExpression_impl(const XPathExpression_impl&); bool operator==(const XPathExpression_impl&); XPathExpression_impl& operator=(const XPathExpression_impl&); diff --git a/include/XPath/impl/xpath_value.hpp b/include/XPath/impl/xpath_value.hpp index a2101314..31701ca6 100644 --- a/include/XPath/impl/xpath_value.hpp +++ b/include/XPath/impl/xpath_value.hpp @@ -14,8 +14,43 @@ namespace Arabica namespace XPath { +template +class Value_base : public XPathValue_impl, public XPathExpression_impl +{ +protected: + Value_base() { } + ~Value_base() { } + +public: + virtual bool evaluateAsBool(const DOM::Node& context) { return asBool(); } + virtual double evaluateAsNumber(const DOM::Node& context) { return asNumber(); } + virtual string_type evaluateAsString(const DOM::Node& context) { return asString(); } + virtual NodeSet evaluateAsNodeSet(const DOM::Node& context) { return asNodeSet(); } + + virtual bool evaluateAsBool(const DOM::Node& context, + const ExecutionContext& executionContext) const + { + return asBool(); + } + virtual double evaluateAsNumber(const DOM::Node& context, + const ExecutionContext& executionContext) const + { + return asNumber(); + } + virtual string_type evaluateAsString(const DOM::Node& context, + const ExecutionContext& executionContext) const + { + return asString(); + } + virtual NodeSet evaluateAsNodeSet(const DOM::Node& context, + const ExecutionContext& executionContext) const + { + return asNodeSet(); + } +}; // class Value_base + template > -class BoolValue : public XPathValue_impl, public XPathExpression_impl +class BoolValue : public Value_base { public: BoolValue(bool value) : @@ -28,10 +63,6 @@ public: { return XPathValue(new BoolValue(value_)); } // evaluate - virtual bool evaluateAsBool(const DOM::Node& context) { return asBool(); } - virtual double evaluateAsNumber(const DOM::Node& context) { return asNumber(); } - virtual string_type evaluateAsString(const DOM::Node& context) { return asString(); } - virtual NodeSet evaluateAsNodeSet(const DOM::Node& context) { return asNodeSet(); } virtual bool asBool() const { return value_; } virtual double asNumber() const { return value_ ? 1 : 0; } @@ -45,7 +76,7 @@ private: }; // class BoolValue template > -class NumericValue : public XPathValue_impl, public XPathExpression_impl +class NumericValue : public Value_base { public: NumericValue(double value) : @@ -58,10 +89,6 @@ public: { return createValue(value_); } // evaluate - virtual bool evaluateAsBool(const DOM::Node& context) { return asBool(); } - virtual double evaluateAsNumber(const DOM::Node& context) { return asNumber(); } - virtual string_type evaluateAsString(const DOM::Node& context) { return asString(); } - virtual NodeSet evaluateAsNodeSet(const DOM::Node& context) { return asNodeSet(); } virtual bool asBool() const { @@ -89,7 +116,7 @@ private: }; // class NumberValue template > -class StringValue : public XPathValue_impl, public XPathExpression_impl +class StringValue : public Value_base { public: StringValue(const char* value) : @@ -104,10 +131,6 @@ public: { return XPathValue(new StringValue(value_)); } // evaluate - virtual bool evaluateAsBool(const DOM::Node& context) { return asBool(); } - virtual double evaluateAsNumber(const DOM::Node& context) { return asNumber(); } - virtual string_type evaluateAsString(const DOM::Node& context) { return asString(); } - virtual NodeSet evaluateAsNodeSet() const { return asNodeSet(); } virtual bool asBool() const { return !string_adaptor::empty(value_); } virtual double asNumber() const @@ -124,7 +147,7 @@ private: }; // class StringValue template > -class NodeSetValue : public XPathValue_impl, public XPathExpression_impl +class NodeSetValue : public Value_base { public: NodeSetValue(const NodeSet& set) : set_(set) { } @@ -139,10 +162,6 @@ public: { return XPathValue(this); } // evaluate - virtual bool evaluateAsBool(const DOM::Node& context) const{ return asBool(); } - virtual double evaluateAsNumber(const DOM::Node& context) const { return asNumber(); } - virtual string_type evaluateAsString(const DOM::Node& context) const { return asString(); } - virtual const NodeSet& evaluateAsNodeSet() const { return asNodeSet(); } virtual bool asBool() const {