diff options
author | John Wiegley <johnw@newartisans.com> | 2006-02-24 10:14:08 +0000 |
---|---|---|
committer | John Wiegley <johnw@newartisans.com> | 2008-04-13 02:41:25 -0400 |
commit | 8043c794133a8de6888371f8942185e5baace0a3 (patch) | |
tree | ab6c338929c135a48ee009a220e4f2d7c0ec56c7 | |
parent | 93ce64fbf78d37e562ae871925aa40707aab73d3 (diff) | |
download | fork-ledger-8043c794133a8de6888371f8942185e5baace0a3.tar.gz fork-ledger-8043c794133a8de6888371f8942185e5baace0a3.tar.bz2 fork-ledger-8043c794133a8de6888371f8942185e5baace0a3.zip |
(parse_value_term): Added support for general @name functions. This
used to mean Python functions, now it will be used for all further
value expression functions. Right now this means the new @min(x,y)
and @max(x,y) functions.
-rw-r--r-- | valexpr.cc | 77 | ||||
-rw-r--r-- | valexpr.h | 1 |
2 files changed, 78 insertions, 0 deletions
@@ -294,6 +294,56 @@ void value_expr_t::compute(value_t& result, const details_t& details) const result = false; break; + case F_FUNC: { + if (constant_s == "min" || constant_s == "max") { + assert(left); + if (! right) { + left->compute(result, details); + break; + } + value_t temp; + left->compute(temp, details); + assert(right->kind == O_ARG); + right->left->compute(result, details); + + if (constant_s == "min") { + if (temp < result) + result = temp; + } else { + if (temp > result) + result = temp; + } + } + else if (constant_s == "price") { + assert(left); + left->compute(result, details); + + std::time_t moment = terminus; + if (right) { + assert(right->kind == O_ARG); + switch (right->left->kind) { + case DATE: + if (details.xact && transaction_has_xdata(*details.xact) && + transaction_xdata_(*details.xact).date) + moment = transaction_xdata_(*details.xact).date; + else if (details.xact) + moment = details.xact->date(); + else if (details.entry) + moment = details.entry->date(); + break; + case CONSTANT_T: + moment = right->left->constant_t; + break; + default: + throw compute_error("Invalid date passed to @price(value,date)"); + } + } + + result = result.value(moment); + } + break; + } + case F_VALUE: { assert(left); left->compute(result, details); @@ -581,6 +631,33 @@ value_expr_t * parse_value_term(std::istream& in) break; } + case '@': { + READ_INTO(in, buf, 255, c, c != '('); + if (c != '(') + unexpected(c, '('); + + node.reset(new value_expr_t(value_expr_t::F_FUNC)); + node->constant_s = buf; + + in.get(c); + if (peek_next_nonws(in) == ')') { + in.get(c); + } else { + value_expr_t * cur = node.get(); + cur->left = parse_value_expr(in, true); + in.get(c); + while (! in.eof() && c == ',') { + cur->right = new value_expr_t(value_expr_t::O_ARG); + cur = cur->right; + cur->left = parse_value_expr(in, true); + in.get(c); + } + if (c != ')') + unexpected(c, ')'); + } + break; + } + case '(': node.reset(parse_value_expr(in, true)); in.get(c); @@ -64,6 +64,7 @@ struct value_expr_t F_PARENT, F_ARITH_MEAN, F_VALUE, + F_FUNC, F_NEG, F_ABS, F_STRIP, |