Minor optimization of how non --empty is handled

This commit is contained in:
John Wiegley 2010-06-07 05:49:20 -04:00
parent 6c8485e6ea
commit 8bd362b5d1
6 changed files with 65 additions and 39 deletions

View file

@ -113,7 +113,7 @@ post_handler_ptr chain_post_handlers(post_handler_ptr base_handler,
post_handler_ptr handler(base_handler);
predicate_t display_predicate;
predicate_t only_predicate;
rounding_error_posts * rounding_handler = NULL;
display_filter_posts * display_filter = NULL;
assert(report.HANDLED(amount_));
expr_t& expr(report.HANDLER(amount_).expr);
@ -141,10 +141,10 @@ post_handler_ptr chain_post_handlers(post_handler_ptr base_handler,
// changed_value_posts adds virtual posts to the list to account for changes
// in market value of commodities, which otherwise would affect the running
// total unpredictably.
if (report.HANDLED(revalued) && ! report.HANDLED(no_rounding)) {
rounding_handler = new rounding_error_posts(handler, report);
handler.reset(rounding_handler);
}
display_filter = new display_filter_posts(handler, report,
report.HANDLED(revalued) &&
! report.HANDLED(no_rounding));
handler.reset(display_filter);
// filter_posts will only pass through posts matching the
// `display_predicate'.
@ -162,7 +162,7 @@ post_handler_ptr chain_post_handlers(post_handler_ptr base_handler,
(! for_accounts_report || report.HANDLED(unrealized)))
handler.reset(new changed_value_posts(handler, report, for_accounts_report,
report.HANDLED(unrealized),
rounding_handler));
display_filter));
// calc_posts computes the running total. When this appears will determine,
// for example, whether filtered posts are included or excluded from the

View file

@ -162,6 +162,7 @@ public:
}
#endif // defined(DEBUG_ON)
DEBUG("expr.calc.when", "Compiling: " << str);
compile(scope);
#if defined(DEBUG_ON)
@ -172,6 +173,7 @@ public:
#endif // defined(DEBUG_ON)
}
DEBUG("expr.calc.when", "Calculating: " << str);
return real_calc(scope);
}

View file

@ -466,27 +466,41 @@ void related_posts::flush()
item_handler<post_t>::flush();
}
rounding_error_posts::rounding_error_posts(post_handler_ptr handler,
report_t& _report)
display_filter_posts::display_filter_posts(post_handler_ptr handler,
report_t& _report,
bool _show_rounding)
: item_handler<post_t>(handler), report(_report),
rounding_account(temps.create_account(_("<Rounding>")))
show_rounding(_show_rounding),
rounding_account(temps.create_account(_("<Rounding>"))),
revalued_account(temps.create_account(_("<Revalued>")))
{
TRACE_CTOR(rounding_error_posts, "post_handler_ptr, report_t&");
TRACE_CTOR(display_filter_posts,
"post_handler_ptr, report_t&, account_t&, bool");
display_amount_expr = report.HANDLER(display_amount_).expr;
display_total_expr = report.HANDLER(display_total_).expr;
}
void rounding_error_posts::output_rounding(post_t& post)
bool display_filter_posts::output_rounding(post_t& post)
{
bind_scope_t bound_scope(report, post);
value_t new_display_total(display_total_expr.calc(bound_scope));
value_t new_display_total;
DEBUG("filters.changed_value.rounding",
"rounding.new_display_total = " << new_display_total);
if (show_rounding) {
new_display_total = display_total_expr.calc(bound_scope);
if (! last_display_total.is_null()) {
if (value_t repriced_amount = display_amount_expr.calc(bound_scope)) {
DEBUG("filters.changed_value.rounding",
"rounding.new_display_total = " << new_display_total);
}
if (post.account == &revalued_account) {
if (show_rounding)
last_display_total = new_display_total;
return true;
}
if (value_t repriced_amount = display_amount_expr.calc(bound_scope)) {
if (! last_display_total.is_null()) {
DEBUG("filters.changed_value.rounding",
"rounding.repriced_amount = " << repriced_amount);
@ -515,16 +529,24 @@ void rounding_error_posts::output_rounding(post_t& post)
/* total= */ precise_display_total,
/* direct_amount= */ true);
}
}
}
if (show_rounding)
last_display_total = new_display_total;
return true;
} else {
// Allow the posting to be displayed if:
// 1. It's display_amount would display as non-zero
// 2. The --empty option was specified
// 3. The account of the posting is <Revalued>
return report.HANDLED(empty);
}
last_display_total = new_display_total;
}
void rounding_error_posts::operator()(post_t& post)
void display_filter_posts::operator()(post_t& post)
{
output_rounding(post);
item_handler<post_t>::operator()(post);
if (output_rounding(post))
item_handler<post_t>::operator()(post);
}
changed_value_posts::changed_value_posts
@ -532,12 +554,13 @@ changed_value_posts::changed_value_posts
report_t& _report,
bool _for_accounts_report,
bool _show_unrealized,
rounding_error_posts * _rounding_handler)
display_filter_posts * _display_filter)
: item_handler<post_t>(handler), report(_report),
for_accounts_report(_for_accounts_report),
show_unrealized(_show_unrealized), last_post(NULL),
revalued_account(temps.create_account(_("<Revalued>"))),
rounding_handler(_rounding_handler)
revalued_account(_display_filter ? _display_filter->revalued_account :
temps.create_account(_("<Revalued>"))),
display_filter(_display_filter)
{
TRACE_CTOR(changed_value_posts, "post_handler_ptr, report_t&, bool");

View file

@ -481,7 +481,7 @@ public:
}
};
class rounding_error_posts : public item_handler<post_t>
class display_filter_posts : public item_handler<post_t>
{
// This filter requires that calc_posts be used at some point
// later in the chain.
@ -489,21 +489,25 @@ class rounding_error_posts : public item_handler<post_t>
expr_t display_amount_expr;
expr_t display_total_expr;
report_t& report;
bool show_rounding;
value_t last_display_total;
temporaries_t temps;
account_t& rounding_account;
rounding_error_posts();
display_filter_posts();
public:
rounding_error_posts(post_handler_ptr handler,
report_t& _report);
account_t& revalued_account;
virtual ~rounding_error_posts() {
TRACE_DTOR(rounding_error_posts);
display_filter_posts(post_handler_ptr handler,
report_t& _report,
bool _show_rounding);
virtual ~display_filter_posts() {
TRACE_DTOR(display_filter_posts);
}
void output_rounding(post_t& post);
bool output_rounding(post_t& post);
virtual void operator()(post_t& post);
@ -538,7 +542,7 @@ class changed_value_posts : public item_handler<post_t>
account_t * gains_equity_account;
account_t * losses_equity_account;
rounding_error_posts * rounding_handler;
display_filter_posts * display_filter;
changed_value_posts();
@ -547,7 +551,7 @@ public:
report_t& _report,
bool _for_accounts_report,
bool _show_unrealized,
rounding_error_posts * _rounding_handler);
display_filter_posts * _display_filter);
virtual ~changed_value_posts() {
TRACE_DTOR(changed_value_posts);

View file

@ -224,9 +224,11 @@ format_accounts::mark_accounts(account_t& account, const bool flat)
if (account.parent &&
(account.has_xflags(ACCOUNT_EXT_VISITED) || (! flat && visited > 0))) {
bind_scope_t bound_scope(report, account);
call_scope_t call_scope(bound_scope);
if ((! flat && to_display > 1) ||
((flat || to_display != 1 ||
account.has_xflags(ACCOUNT_EXT_VISITED)) &&
(report.HANDLED(empty) || report.fn_display_total(call_scope)) &&
disp_pred(bound_scope))) {
account.xdata().add_flags(ACCOUNT_EXT_TO_DISPLAY);
DEBUG("account.display", "Marking account as TO_DISPLAY");

View file

@ -140,11 +140,6 @@ void report_t::normalize_options(const string& verb)
if (verb == "print")
HANDLER(limit_).on(string("?normalize"), "actual");
if (! HANDLED(empty))
HANDLER(display_).on(string("?normalize"),
string("(post?(display_amount|account=\"") +
_("<Revalued>") + "\"):display_total)");
if (verb[0] != 'b' && verb[0] != 'r')
HANDLER(base).on_only(string("?normalize"));