I have the following tricky problem: I have implemented a (rather complicated) class which represents mathematical functions in a multiwavelet basis. Since operations like +, – and * are quite natural in this context, I have implemented overloaded operators for this class:
FunctionTree<D> operator+(FunctionTree<D> &inpTree);
FunctionTree<D> operator-(FunctionTree<D> &inpTree);
FunctionTree<D> operator*(FunctionTree<D> &inpTree);
There operators work finer in simple, non-chained operations, and even in some cases when chaining the operators. Statements like
FunctionTree<3> y = a * b + c;
FunctionTree<3> z = a * b + b;
compile and seemingly work fine. The first line is actually ok, but the second line causes valgrind to tell you grim stories about memory being freed inside already freed regions and uninitialized variables being accessed. Furthermore, a statement like
FunctionTree<D> y = a + b * c;
will not even compile, because I have not defined (an ambiguous operator taking an actual object, not a reference, as argument). Of course the solution is clear: All arguments, and methods ought to be made const, and perhaps even return a const object or reference. Unfortunately this is not possible, since NONE of the objects involved are constant during the operations! This may sound strange, but this is an unavoidable consequence of the mathematics involved. I can fake it, using const_cast, but the code is still wrong!
Is there a way to solve this problem? The only solution I have currently is to make the return objects const, thus effectively disabling the operator chaining.
Regards, .jonas.
You can use proxies instead of real values, and proxies can be constant, as they are not going to be changed. Below is a small example of how it might look like. Be aware that all the temporaries are still going to be created in that example but if you want to be smart, you can just save the operations, not the actual results of operations, and calculate only when someone wants to finally get result or a part of it. It might even speed up your code enormously as it helped APL
Also, you might want to make most of the members private.