summaryrefslogtreecommitdiff
path: root/project2/variables.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'project2/variables.cpp')
-rw-r--r--project2/variables.cpp59
1 files changed, 56 insertions, 3 deletions
diff --git a/project2/variables.cpp b/project2/variables.cpp
index 09ea36e..c6a65f1 100644
--- a/project2/variables.cpp
+++ b/project2/variables.cpp
@@ -8,6 +8,9 @@
#include <boost/tokenizer.hpp>
#include <boost/foreach.hpp>
#include <boost/algorithm/string/predicate.hpp>
+#include <boost/lexical_cast.hpp>
+#include <boost/function.hpp>
+#include <boost/bind.hpp>
class VariableLiteral : public VariableImpl {
public:
@@ -19,6 +22,7 @@ class VariableLiteral : public VariableImpl {
class VariableImplDyn : public VariableImpl {
public:
VariableImplDyn(const Glib::ustring & src) : VariableImpl(src), cacheValid(false) { }
+ VariableImplDyn(const Glib::ustring & src, boost::optional<Glib::ustring> def) : VariableImpl(src, def), cacheValid(false) { }
virtual const Glib::ustring & value() const = 0;
protected:
@@ -94,6 +98,15 @@ class VariableParent : public VariableImplDyn, public RowUser {
depth(src.length() - source.length()),
dep(d)
{
+ bind();
+ }
+ VariableParent(const Glib::ustring & name, unsigned int d) :
+ VariableImplDyn(name, NULL),
+ row(NULL),
+ depth(d),
+ dep(NULL)
+ {
+ bind();
}
~VariableParent()
{
@@ -120,7 +133,7 @@ class VariableParent : public VariableImplDyn, public RowUser {
row->use(dep);
}
}
- cache = row->getCurrentValue(name);
+ getValue(cache, row);
}
catch (PerRowValues::ParentOutOfRange) {
if (!defaultValue) {
@@ -143,9 +156,31 @@ class VariableParent : public VariableImplDyn, public RowUser {
cacheValid = false;
}
protected:
+ static void assignHelper(Glib::ustring & dest, const Glib::ustring & src) {
+ dest = src;
+ }
+ void bind()
+ {
+ if (name[0] == '!') {
+ if (name == "!rownum") {
+ getValue = boost::bind(&assignHelper, _1,
+ boost::bind(&boost::lexical_cast<Glib::ustring, unsigned int>,
+ boost::bind(&PerRowValues::getRowNum, _2)));
+ }
+ else {
+ throw PerRowValues::FieldDoesNotExist();
+ }
+ }
+ else {
+ typedef const Glib::ustring & (PerRowValues::*gCV)(const Glib::ustring &) const;
+ getValue = boost::bind(&assignHelper, _1,
+ boost::bind((gCV)&PerRowValues::getCurrentValue, _2, name));
+ }
+ }
mutable const PerRowValues * row;
const size_t depth;
const RowUser * dep;
+ boost::function2<void, Glib::ustring &, const PerRowValues *> getValue;
};
class VariableParse : public VariableImplDyn, public RowUser {
@@ -190,16 +225,21 @@ Variable::Variable(const Glib::ustring & s) :
{
}
-Variable::Variable(xmlpp::Attribute * a) :
+Variable::Variable(const xmlpp::Attribute * a) :
var(create(a->get_value()))
{
}
-Variable::Variable(xmlpp::Element * e) :
+Variable::Variable(const xmlpp::Element * e) :
var(create(e->get_child_text()->get_content()))
{
}
+Variable::Variable(VariableImpl * v) :
+ var(v)
+{
+}
+
Variable::VariableImplPtr
Variable::create(const Glib::ustring & s, RowUser * dep)
{
@@ -224,6 +264,19 @@ Variable::create(const Glib::ustring & s, RowUser * dep)
}
}
+Variable
+Variable::makeParent(const Glib::ustring & n, unsigned int d)
+{
+ return Variable(new VariableParent(n, d));
+}
+
+VariableImpl::VariableImpl(const Glib::ustring & src, boost::optional<Glib::ustring> def) :
+ source(src),
+ name(src),
+ defaultValue(def)
+{
+}
+
VariableImpl::VariableImpl(const Glib::ustring & src) :
source(src)
{