I would go with Charles Graham's hybrid suggestion, but I want to add my two cents as to why.
A lot of the above suggestions talk about complexity and optimization, but forget this all goes out the window when you factor in the consumer of your class. If you are the only consumer, and you used the first implementation, chances are you would remember to:
double subTotal = myOrder.TotalCash;
double tax = subTotal * 0.05;
double shipping = subTotal > 100 ? 0 : 5.95;
double grandTotal = subTotal + tax + shipping;
OutputToUser(subTotal, tax, shipping, grandTotal);
Other people might not. Seeing that myOrder.TotalCash
is a property, not a method, at least I would assume it is a cached value. That is, accessing subTotal
in the above example is comparable in efficiency as accessing myOrder.TotalCash
. Not realizing there's a calculation going on behind the scenes, they write:
double tax = myOrder.TotalCash * 0.05;
double shipping = myOrder.TotalCash > 100 ? 0 : 5.95;
double grandTotal = myOrder.TotalCash + tax + shipping;
OutputToUser(myOrder.TotalCash, tax, shipping, grandTotal);
leaving myOrder.TotalCash
to stand for the subtotal. Now, it has been calculated 4 times instead of 1.
In summary, I'm sure I'm not the only one who believes that a property represents a variable or cached value and a method processes something and returns a value. It makes sense to store CalculateTotalCash()
and only call it once, because you expect it to be a performance hit. On the other hand, you expect TotalCash
to be a cached value and can access it at will. Thus it is important to only recalculate TotalCash
when it changes.
The hybrid suggestion wins in the case of multiple sets between reads. That way you're not wasting time calculating a value to be thrown away.