summaryrefslogtreecommitdiff
path: root/src/value.h
diff options
context:
space:
mode:
Diffstat (limited to 'src/value.h')
-rw-r--r--src/value.h421
1 files changed, 166 insertions, 255 deletions
diff --git a/src/value.h b/src/value.h
index b1e0459d..a6bb091f 100644
--- a/src/value.h
+++ b/src/value.h
@@ -65,92 +65,101 @@ class value_t
typedef std::vector<value_t> sequence_t;
enum type_t {
+ VOID,
BOOLEAN,
- INTEGER,
DATETIME,
+ INTEGER,
AMOUNT,
BALANCE,
BALANCE_PAIR,
STRING,
+ SEQUENCE,
XML_NODE,
- POINTER,
- SEQUENCE
+ POINTER
} type;
- value_t() {
+ value_t() : type(VOID) {
TRACE_CTOR(value_t, "");
- *((long *) data) = 0;
- type = INTEGER;
}
- value_t(const value_t& val) : type(INTEGER) {
+ value_t(const value_t& val) : type(VOID) {
TRACE_CTOR(value_t, "copy");
*this = val;
}
value_t(const bool val) {
TRACE_CTOR(value_t, "const bool");
- *((bool *) data) = val;
type = BOOLEAN;
+ as_boolean() = val;
}
value_t(const long val) {
TRACE_CTOR(value_t, "const long");
- *((long *) data) = val;
type = INTEGER;
+ as_long() = val;
}
value_t(const moment_t val) {
TRACE_CTOR(value_t, "const moment_t");
- *((moment_t *) data) = val;
type = DATETIME;
- }
- value_t(const unsigned long val) {
- TRACE_CTOR(value_t, "const unsigned long");
- new((amount_t *) data) amount_t(val);
- type = AMOUNT;
+ new((moment_t *) data) moment_t(val);
}
value_t(const double val) {
TRACE_CTOR(value_t, "const double");
+ type = AMOUNT;
new((amount_t *) data) amount_t(val);
+ }
+ value_t(const unsigned long val) {
+ TRACE_CTOR(value_t, "const unsigned long");
type = AMOUNT;
+ new((amount_t *) data) amount_t(val);
}
value_t(const string& val, bool literal = false) {
TRACE_CTOR(value_t, "const string&, bool");
if (literal) {
- type = INTEGER;
- set_string(val);
+ type = STRING;
+ new((string *) data) string(val);
} else {
- new((amount_t *) data) amount_t(val);
type = AMOUNT;
+ new((amount_t *) data) amount_t(val);
}
}
- value_t(const char * val) {
+ value_t(const char * val, bool literal = false) {
TRACE_CTOR(value_t, "const char *");
- new((amount_t *) data) amount_t(val);
- type = AMOUNT;
+ if (literal) {
+ type = STRING;
+ new((string *) data) string(val);
+ } else {
+ type = AMOUNT;
+ new((amount_t *) data) amount_t(val);
+ }
}
value_t(const amount_t& val) {
TRACE_CTOR(value_t, "const amount_t&");
- new((amount_t *)data) amount_t(val);
type = AMOUNT;
+ new((amount_t *)data) amount_t(val);
}
- value_t(const balance_t& val) : type(INTEGER) {
+ value_t(const balance_t& val) : type(VOID) {
TRACE_CTOR(value_t, "const balance_t&");
- *this = val;
+ type = BALANCE;
+ new((balance_t *)data) balance_t(val);
}
- value_t(const balance_pair_t& val) : type(INTEGER) {
+ value_t(const balance_pair_t& val) : type(VOID) {
TRACE_CTOR(value_t, "const balance_pair_t&");
- *this = val;
+ type = BALANCE_PAIR;
+ new((balance_pair_t *)data) balance_pair_t(val);
+ }
+ value_t(const sequence_t& val) {
+ TRACE_CTOR(value_t, "const sequence_t&");
+ type = SEQUENCE;
+ new((sequence_t *)data) sequence_t(val);
}
- value_t(xml::node_t * xml_node) : type(INTEGER) { // gets set in =
+ value_t(xml::node_t * xml_node) {
TRACE_CTOR(value_t, "xml::node_t *");
- *this = xml_node;
+ type = XML_NODE;
+ as_xml_node() = xml_node;
}
- value_t(void * item) : type(INTEGER) { // gets set in =
+ value_t(void * item) {
TRACE_CTOR(value_t, "void *");
- *this = item;
- }
- value_t(sequence_t * seq) : type(INTEGER) { // gets set in =
- TRACE_CTOR(value_t, "sequence_t *");
- *this = seq;
+ type = POINTER;
+ as_pointer() = item;
}
~value_t() {
@@ -159,184 +168,125 @@ class value_t
}
void destroy();
- void simplify();
+ value_t simplify() const {
+ value_t temp = *this;
+ temp.in_place_simplify();
+ return temp;
+ }
+ void in_place_simplify();
value_t& operator=(const value_t& val);
-#if 0
- value_t& operator=(const bool val) {
- if ((bool *) data != &val) {
+
+ value_t& set_string(const string& str = "") {
+ if (type != STRING) {
destroy();
- *((bool *) data) = val;
- type = BOOLEAN;
+ type = STRING;
}
+ as_string() = str;
return *this;
}
- value_t& operator=(const long val) {
- if ((long *) data != &val) {
- destroy();
- *((long *) data) = val;
- type = INTEGER;
- }
- return *this;
+
+ bool& as_boolean() {
+ assert(type == BOOLEAN);
+ return *(bool *) data;
}
- value_t& operator=(const moment_t val) {
- if ((moment_t *) data != &val) {
- destroy();
- *((moment_t *) data) = val;
- type = DATETIME;
- }
- return *this;
+ const bool& as_boolean() const {
+ assert(type == BOOLEAN);
+ return *(bool *) data;
}
- value_t& operator=(const unsigned long val) {
- return *this = amount_t(val);
+ long& as_long() {
+ assert(type == INTEGER);
+ return *(long *) data;
}
- value_t& operator=(const double val) {
- return *this = amount_t(val);
+ const long& as_long() const {
+ assert(type == INTEGER);
+ return *(long *) data;
}
- value_t& operator=(const string& val) {
- return *this = amount_t(val);
+ moment_t& as_datetime() {
+ assert(type == DATETIME);
+ return *(moment_t *) data;
}
- value_t& operator=(const char * val) {
- return *this = amount_t(val);
+ const moment_t& as_datetime() const {
+ assert(type == DATETIME);
+ return *(moment_t *) data;
}
- value_t& operator=(const amount_t& val) {
- if (type == AMOUNT &&
- (amount_t *) data == &val)
- return *this;
-
- if (val.realzero()) {
- return *this = 0L;
- } else {
- destroy();
- new((amount_t *)data) amount_t(val);
- type = AMOUNT;
- }
- return *this;
+ amount_t& as_amount() {
+ assert(type == AMOUNT);
+ return *(amount_t *) data;
}
- value_t& operator=(const balance_t& val) {
- if (type == BALANCE &&
- (balance_t *) data == &val)
- return *this;
-
- if (val.realzero()) {
- return *this = 0L;
- }
- else if (val.amounts.size() == 1) {
- return *this = (*val.amounts.begin()).second;
- }
- else {
- destroy();
- new((balance_t *)data) balance_t(val);
- type = BALANCE;
- return *this;
- }
+ const amount_t& as_amount() const {
+ assert(type == AMOUNT);
+ return *(amount_t *) data;
}
- value_t& operator=(const balance_pair_t& val) {
- if (type == BALANCE_PAIR &&
- (balance_pair_t *) data == &val)
- return *this;
-
- if (val.realzero()) {
- return *this = 0L;
- }
- else if (! val.cost) {
- return *this = val.quantity;
- }
- else {
- destroy();
- new((balance_pair_t *)data) balance_pair_t(val);
- type = BALANCE_PAIR;
- return *this;
- }
+ balance_t& as_balance() {
+ assert(type == BALANCE);
+ return *(balance_t *) data;
}
- value_t& operator=(xml::node_t * xml_node) {
- assert(xml_node);
- if (type == XML_NODE && *(xml::node_t **) data == xml_node)
- return *this;
-
- if (! xml_node) {
- type = XML_NODE;
- return *this = 0L;
- }
- else {
- destroy();
- *(xml::node_t **)data = xml_node;
- type = XML_NODE;
- return *this;
- }
+ const balance_t& as_balance() const {
+ assert(type == BALANCE);
+ return *(balance_t *) data;
}
- value_t& operator=(void * item) {
- assert(item);
- if (type == POINTER && *(void **) data == item)
- return *this;
-
- if (! item) {
- type = POINTER;
- return *this = 0L;
- }
- else {
- destroy();
- *(void **)data = item;
- type = POINTER;
- return *this;
- }
+ balance_pair_t& as_balance_pair() {
+ assert(type == BALANCE_PAIR);
+ return *(balance_pair_t *) data;
}
- value_t& operator=(sequence_t * seq) {
- assert(seq);
- if (type == SEQUENCE && *(sequence_t **) data == seq)
- return *this;
-
- if (! seq) {
- type = SEQUENCE;
- return *this = 0L;
- }
- else {
- destroy();
- *(sequence_t **)data = seq;
- type = SEQUENCE;
- return *this;
- }
+ const balance_pair_t& as_balance_pair() const {
+ assert(type == BALANCE_PAIR);
+ return *(balance_pair_t *) data;
+ }
+ string& as_string() {
+ assert(type == STRING);
+ return *(string *) data;
+ }
+ const string& as_string() const {
+ assert(type == STRING);
+ return *(string *) data;
+ }
+ sequence_t& as_sequence() {
+ assert(type == SEQUENCE);
+ return *(sequence_t *) data;
+ }
+ const sequence_t& as_sequence() const {
+ assert(type == SEQUENCE);
+ return *(sequence_t *) data;
}
-#endif
- value_t& set_string(const string& str = "") {
- if (type != STRING) {
- destroy();
- *(string **) data = new string(str);
- type = STRING;
- } else {
- **(string **) data = str;
- }
- return *this;
+ xml::node_t *& as_xml_node() {
+ assert(type == XML_NODE);
+ return *(xml::node_t **) data;
+ }
+ xml::node_t * as_xml_node() const {
+ assert(type == XML_NODE);
+ return *(xml::node_t **) data;
+ }
+ void *& as_pointer() {
+ assert(type == POINTER);
+ return *(void **) data;
+ }
+ void * as_pointer() const {
+ assert(type == POINTER);
+ return *(void **) data;
}
- bool& to_boolean();
- long& to_long();
- moment_t& to_datetime();
- amount_t& to_amount();
- balance_t& to_balance();
- balance_pair_t& to_balance_pair();
- string& to_string();
- xml::node_t *& to_xml_node();
- void *& to_pointer();
- sequence_t *& to_sequence();
+ bool to_boolean() const;
+ long to_long() const;
+ moment_t to_datetime() const;
+ amount_t to_amount() const;
+ balance_t to_balance() const;
+ balance_pair_t to_balance_pair() const;
+ string to_string() const;
+ sequence_t to_sequence() const;
value_t& operator[](const int index) {
- sequence_t * seq = to_sequence();
- assert(seq);
- return (*seq)[index];
+ return as_sequence()[index];
}
void push_back(const value_t& val) {
- sequence_t * seq = to_sequence();
- assert(seq);
- return seq->push_back(val);
+ return as_sequence().push_back(val);
}
std::size_t size() const {
- sequence_t * seq = const_cast<value_t&>(*this).to_sequence();
- assert(seq);
- return seq->size();
+ return as_sequence().size();
}
value_t& operator+=(const value_t& val);
@@ -344,42 +294,42 @@ class value_t
value_t& operator*=(const value_t& val);
value_t& operator/=(const value_t& val);
- int compare(const value_t& val) const;
-
- bool operator==(const value_t& val) const {
- return compare(val) == 0;
- }
-#if 0
- template <typename T>
- bool operator==(const T& val) const {
- return *this == value_t(val);
- }
-#endif
-
- bool operator<(const value_t& val) const {
- return compare(val) < 0;
- }
-#if 0
- template <typename T>
- bool operator<(const T& val) const {
- return *this < value_t(val);
+ bool operator==(const value_t& val) const;
+ bool operator<(const value_t& val) const;
+ //bool operator>(const value_t& val) const;
+
+ string label(optional<type_t> the_type = optional<type_t>()) const {
+ switch (the_type ? *the_type : type) {
+ case VOID:
+ return "an uninitialized value";
+ case BOOLEAN:
+ return "a boolean";
+ case INTEGER:
+ return "an integer";
+ case DATETIME:
+ return "a date/time";
+ case AMOUNT:
+ return "an amount";
+ case BALANCE:
+ return "a balance";
+ case BALANCE_PAIR:
+ return "a balance pair";
+ case STRING:
+ return "a string";
+ case SEQUENCE:
+ return "a sequence";
+ case XML_NODE:
+ return "an xml node";
+ case POINTER:
+ return "a pointer";
+ default:
+ assert(false);
+ break;
+ }
}
-#endif
-
+
operator bool() const;
-#if 0
- operator long() const;
- operator unsigned long() const;
- operator double() const;
- operator moment_t() const;
- operator string() const;
- operator char *() const;
- operator amount_t() const;
- operator balance_t() const;
- operator balance_pair_t() const;
-#endif
-
value_t operator-() const {
return negate();
}
@@ -429,45 +379,6 @@ class value_t
friend std::ostream& operator<<(std::ostream& out, const value_t& val);
};
-#if 0
-template <typename T>
-value_t::operator T() const
-{
- switch (type) {
- case BOOLEAN:
- return *(bool *) data;
- case INTEGER:
- return *(long *) data;
- case DATETIME:
- return *(moment_t *) data;
- case AMOUNT:
- return *(amount_t *) data;
- case BALANCE:
- return *(balance_t *) data;
- case STRING:
- return **(string **) data;
- case XML_NODE:
- return *(xml::node_t **) data;
- case POINTER:
- return *(void **) data;
- case SEQUENCE:
- return *(sequence_t **) data;
-
- default:
- assert(0);
- break;
- }
- assert(0);
- return 0;
-}
-
-template <> value_t::operator bool() const;
-template <> value_t::operator long() const;
-template <> value_t::operator moment_t() const;
-template <> value_t::operator double() const;
-template <> value_t::operator string() const;
-#endif
-
std::ostream& operator<<(std::ostream& out, const value_t& val);
#if 0