which one do you prefer? (of course getSize doesn't make any complicated counting, just returning member value)
void method1(Object & o)
{
int size = o.getSize();
someAction(size);
someOtherAction(size);
}
or
void method2(Object & o)
{
someAction(o.getSize());
someOtherAction(o.getSize());
}
I know I can measure which one is faster but I want some comments... Not just executing time related... eg. if you are prefer method2, how many times maximally do you use o.getSize and what is the number what make you use method1 way?
Any best practices? (imagine even different types then int)
TY
I would go for method 1 not just because it's probably marginally faster, but mostly because it means I don't have to worry about whether the called method has any side effects.
Also, if this is called in a multi-threaded program this ensures that I'm always using my value of size - otherwise it might have changed between the two calls. Of course there may be cases where you explicitly might want to notice that change, in which case use method 2.
(and yes, per other answers, make size a const int to ensure that it's not modified if it's passed by reference to something else).
Since you don't want size to change when you call someAction() or someOtherAction() (as it cannot when it is the return value of a function), consider:
void method3(const Object& o)
{
const int size = o.getSize();
someAction(size);
someOtherAction(size);
}
getSize() may be simple, or it may be doing a costly calculation. Also, the size of o may be changed by another thread between your calls to someAction() and someOtherAction().
I would prefer the first approach. Calling a function repeatedly doesn't seem good to me, especially if the returned value is same everytime. The first approach also avoids the overhead of calling a function repeatedly.
When I call a function that returns something multiple times (about more than 2-3 times) I usually save the returned value in a local variable. That's because I appreciate program speed more than memory saving. Not that memory wouldn't be important. It just depends on the situations.
Calling a function that doesn't take a lot of time to execute isn't time consuming, but a function with several loops being called a large number of times would send your program into long waits.
The first one will eliminate unnecessary calls to a function, therefore I prefer method1() as the code also looks a bit cleaner.
However, you should be aware that depending on context, they may produce different results. Say, if size changes in someAction(), and you use value stored in size variable, you may not get the desired result.
Repeatedly calling any function when the result wont change is a waste, so I would always go with the first method.
Related
Lets say I have a very costly function that checks if an object has a certain property. Another function would then, depending on whether the object has the property, do different things.
If I have previously checked for the property, would it be recomputed by the second function, or is it known?
I'm thinking of something like:
bool check_property(object){
// very costly operations...
}
void do_something(object){
if(check_property) {do thing}
else {do different thing}
}
Would the if in do_something recompute check_property?
There are several factors that have to come together for the compiler to avoid recomputing the function's result:
The compiler has to know which input values the function's result depends on. This knowledge is very difficult to extract from the code in general case. In some implementations you can help the compiler by using compiler-specific means to declare your function as "pure" or "const" (GCC function attributes)
The compiler has to make sure that the above input values did not change since the previous call to the same function. This might be very easy in some specific case, but is also very difficult in general case.
The compiler has to have the result of previous computation readily available. Normally, compilers do not deliberately "cache" such results in some dedicated storage for future reuse. The optimization in question is typically applied only when you make multiple calls to the same function in "close proximity" to each other, meaning that the previous result is easy to keep till the moment of the next call.
So, the optimization in question is certainly possible. But it is something you should expect to see in simple and very localized cases, like calling sqrt(x) several times in a row for the same value of x (in the same expression, in the same cycle and such). But for more complicated functions it is typically going to be your responsibility to either somehow avoid making multiple calls to the same expensive function, or maybe memoize the results if you believe it can benefit your code.
Unless the compiler can prove that check_property has no side effects and that all the data it depends from is the same, it is not allowed to remove the call; for all practical purposes, unless your function body is known in the current TU, it is pretty much trivial and the multiple calls happen in the same function, calling again will execute its code again. I don't know of any compiler that establish automatically a cross-call cache, because it's not trivial at all.
If you need to cache the computed values, in general you will have to do it yourself; keep in mind that it's not always trivial - generally the ugly beasts to tackle are cache invalidation (how do I know that the data used to calculate the value didn't change from the last time I calculated it? how do I avoid the cache size getting out of hand?) and multithreading concerns (is this code going to be called from multiple threads? if so, I have to synchronize the access to the cache, possibly adding coupling between unrelated threads and, in extreme cases, killing the efficiency of the cache itself).
To answer your question, yes. It will rerun it. If you want to make sure that the code doesn't run it again every time you call do_something, try adding a variable in your class that will tell you if you already ran it:
bool check_property(object){
// very costly operations...
return true;
}
void do_something(object,bool has_run){
if(has_run) {do thing}
else {do different thing}
}
void main() {
bool has_run = false;
has_run = check_property(object);
do_something(object,has_run);
}
There are of course multiple ways of doing this, and this might not fit your criteria, but it is a possible way of doing it!
I just realized that this isn't really how C++ works since everything is not in classes unlike Java. Instead you can just pass the value as an argument to the function itself. So, I have edited my code.
Suppose I have a function that will return a large data structure, with the intention that the caller will immediately copy the return value:
Large large()
{
return Large();
}
Now suppose I do not want to rely on any kind of compiler optimizations such as return value optimization etc. Also suppose that I cannot rely on the C++11 move constructor. I would like to gather some opinions on the "correctness" of the following code:
const Large& large()
{
static Large large;
large = Large();
return large;
}
It should work as intended, but is it poor style to return a reference to a static local even if it is const qualified?
It all depends on what should work as expected means. In this case all callers will share references to the exact same variable. Also note that if callers will copy, then you are effectively disabling RVO (Return Value Optimization), which will work in all current compilers [*].
I would stay away from that approach as much as possible, it is not idiomatic and will probably cause confusion in many cases.
[*]The calling convention in all compilers I know of determines that a function that returns a large (i.e. does not fit a register) variable receives a hidden pointer to the location in which the caller has allocated the space for the variable. That is, the optization is forced by the calling convention.
I don't think there's any issue with doing this. So long as this code base is, and forever will be, single threaded.
Do this on a multithreaded piece of code, and you might never be able to figure out why your data are occasionally being randomly corrupted.
I have a class which has a constructor that takes a const char*. It is:
c::c(const char* str) {
a = 32;
f = 0;
data = new char[strlen(str)];
memcpy(data, str, strlen(str));
}
And a function which takes one of them:
int foo(c& cinst);
You can call this function either by passing it an instance of a c:
c cinst("asdf");
foo(cinst);
or, because we have explicit initialization, you can do:
foo("asdf");
which will make a c by passing the constructor "asdf" and then pass the resulting object to foo.
However, this seems like it might be quite a bit less efficient than just overloading foo to take a const char*. Is it worth doing the overload for the speed or is the performance impact so small that it's a waste of space to make an overload? I'm trying to make my program as fast as possible, so speed is an important factor, so is size, but not so much.
What will foo be doing with that const char*? If it's just going to make it own c object, then there's no point.
If it is going to use the char* directly (and the existing foo just pulled the char* out of the c object), then it would be better to write an overload.
It won't take zero time so it is one of the tradeoffs you have to take, speed versus api clarity. Of course it will depend on what you are doing in your function that takes a const char*, are you constructing a c object? In which case just offer the function with the c class interface.
This sort of question is best answered with a profiler.
Looking at the assembler code for it may also provide a clue.
It's situational. It really depends on just how much is really going on inside a constructor in a given situation and how many times that code is actually being executed.
In the example you give, those are pretty trivial operations in that constructor. On any reasonable modern processor those operations are going to be very very quick. So unless that code is being executed a huge number of times per second or more, then I wouldn't even worry about it. (Of course the value of "huge" depends on what kind of machine you expect to run this on. For this constructor, on a typical desktop processor, I wouldn't even begin to worry until it gets up into the scale of at least hundreds-of-thousands of times per second.)
If this construction code does run some huge number of times, then you still ought to profile it and determine for sure if it's having a noticeable impact compared to everything else going on in your program. Optimization is a tricky thing. Sometimes what your gut feeling says is inefficient actually has little impact on the end results. Measurement is always to way to determine where you should actually be spending your time to most effectively make your program run faster.
I've seen numerous arguments that using a return value is preferable to out parameters. I am convinced of the reasons why to avoid them, but I find myself unsure if I'm running into cases where it is unavoidable.
Part One of my question is: What are some of your favorite/common ways of getting around using an out parameter? Stuff along the lines: Man, in peer reviews I always see other programmers do this when they could have easily done it this way.
Part Two of my question deals with some specific cases I've encountered where I would like to avoid an out parameter but cannot think of a clean way to do so.
Example 1:
I have a class with an expensive copy that I would like to avoid. Work can be done on the object and this builds up the object to be expensive to copy. The work to build up the data is not exactly trivial either. Currently, I will pass this object into a function that will modify the state of the object. This to me is preferable to new'ing the object internal to the worker function and returning it back, as it allows me to keep things on the stack.
class ExpensiveCopy //Defines some interface I can't change.
{
public:
ExpensiveCopy(const ExpensiveCopy toCopy){ /*Ouch! This hurts.*/ };
ExpensiveCopy& operator=(const ExpensiveCopy& toCopy){/*Ouch! This hurts.*/};
void addToData(SomeData);
SomeData getData();
}
class B
{
public:
static void doWork(ExpensiveCopy& ec_out, int someParam);
//or
// Your Function Here.
}
Using my function, I get calling code like this:
const int SOME_PARAM = 5;
ExpensiveCopy toModify;
B::doWork(toModify, SOME_PARAM);
I'd like to have something like this:
ExpensiveCopy theResult = B::doWork(SOME_PARAM);
But I don't know if this is possible.
Second Example:
I have an array of objects. The objects in the array are a complex type, and I need to do work on each element, work that I'd like to keep separated from the main loop that accesses each element. The code currently looks like this:
std::vector<ComplexType> theCollection;
for(int index = 0; index < theCollection.size(); ++index)
{
doWork(theCollection[index]);
}
void doWork(ComplexType& ct_out)
{
//Do work on the individual element.
}
Any suggestions on how to deal with some of these situations? I work primarily in C++, but I'm interested to see if other languages facilitate an easier setup. I have encountered RVO as a possible solution, but I need to read up more on it and it sounds like a compiler specific feature.
I'm not sure why you're trying to avoid passing references here. It's pretty much these situations that pass-by-reference semantics exist.
The code
static void doWork(ExpensiveCopy& ec_out, int someParam);
looks perfectly fine to me.
If you really want to modify it then you've got a couple of options
Move doWork so that's it's a member of ExpensiveCopy (which you say you can't do, so that's out)
return a (smart) pointer from doWork instead of copying it. (which you don't want to do as you want to keep things on the stack)
Rely on RVO (which others have pointed out is supported by pretty much all modern compilers)
Every useful compiler does RVO (return value optimization) if optimizations are enabled, thus the following effectively doesn't result in copying:
Expensive work() {
// ... no branched returns here
return Expensive(foo);
}
Expensive e = work();
In some cases compilers can apply NRVO, named return value optimization, as well:
Expensive work() {
Expensive e; // named object
// ... no branched returns here
return e; // return named object
}
This however isn't exactly reliable, only works in more trivial cases and would have to be tested. If you're not up to testing every case, just use out-parameters with references in the second case.
IMO the first thing you should ask yourself is whether copying ExpensiveCopy really is so prohibitive expensive. And to answer that, you will usually need a profiler. Unless a profiler tells you that the copying really is a bottleneck, simply write the code that's easier to read: ExpensiveCopy obj = doWork(param);.
Of course, there are indeed cases where objects cannot be copied for performance or other reasons. Then Neil's answer applies.
In addition to all comments here I'd mention that in C++0x you'd rarely use output parameter for optimization purpose -- because of Move Constructors (see here)
Unless you are going down the "everything is immutable" route, which doesn't sit too well with C++. you cannot easily avoid out parameters. The C++ Standard Library uses them, and what's good enough for it is good enough for me.
As to your first example: return value optimization will often allow the returned object to be created directly in-place, instead of having to copy the object around. All modern compilers do this.
What platform are you working on?
The reason I ask is that many people have suggested Return Value Optimization, which is a very handy compiler optimization present in almost every compiler. Additionally Microsoft and Intel implement what they call Named Return Value Optimization which is even more handy.
In standard Return Value Optimization your return statement is a call to an object's constructor, which tells the compiler to eliminate the temporary values (not necessarily the copy operation).
In Named Return Value Optimization you can return a value by its name and the compiler will do the same thing. The advantage to NRVO is that you can do more complex operations on the created value (like calling functions on it) before returning it.
While neither of these really eliminate an expensive copy if your returned data is very large, they do help.
In terms of avoiding the copy the only real way to do that is with pointers or references because your function needs to be modifying the data in the place you want it to end up in. That means you probably want to have a pass-by-reference parameter.
Also I figure I should point out that pass-by-reference is very common in high-performance code for specifically this reason. Copying data can be incredibly expensive, and it is often something people overlook when optimizing their code.
As far as I can see, the reasons to prefer return values to out parameters are that it's clearer, and it works with pure functional programming (you can get some nice guarantees if a function depends only on input parameters, returns a value, and has no side effects). The first reason is stylistic, and in my opinion not all that important. The second isn't a good fit with C++. Therefore, I wouldn't try to distort anything to avoid out parameters.
The simple fact is that some functions have to return multiple things, and in most languages this suggests out parameters. Common Lisp has multiple-value-bind and multiple-value-return, in which a list of symbols is provided by the bind and a list of values is returned. In some cases, a function can return a composite value, such as a list of values which will then get deconstructed, and it isn't a big deal for a C++ function to return a std::pair. Returning more than two values this way in C++ gets awkward. It's always possible to define a struct, but defining and creating it will often be messier than out parameters.
In some cases, the return value gets overloaded. In C, getchar() returns an int, with the idea being that there are more int values than char (true in all implementations I know of, false in some I can easily imagine), so one of the values can be used to denote end-of-file. atoi() returns an integer, either the integer represented by the string it's passed or zero if there is none, so it returns the same thing for "0" and "frog". (If you want to know whether there was an int value or not, use strtol(), which does have an out parameter.)
There's always the technique of throwing an exception in case of an error, but not all multiple return values are errors, and not all errors are exceptional.
So, overloaded return values causes problems, multiple value returns aren't easy to use in all languages, and single returns don't always exist. Throwing an exception is often inappropriate. Using out parameters is very often the cleanest solution.
Ask yourself why you have some method that performs work on this expensive to copy object in the first place. Say you have a tree, would you send the tree off into some building method or else give the tree its own building method? Situations like this come up constantly when you have a little bit off design but tend to fold into themselves when you have it down pat.
I know in practicality we don't always get to change every object at all, but passing in out parameters is a side effect operation, and it makes it much harder to figure out what's going on, and you never really have to do it (except as forced by working within others' code frameworks).
Sometimes it is easier, but it's definitely not desirable to use it for no reason (if you've suffered through a few large projects where there's always half a dozen out parameters you'll know what I mean).
I have an inline member function defined under class MyClass
int MyClass::myInlineFunction();
This function is called from several places in my code.
There are two ways to call this function
Case 1: Using this every time the function is called.
mobj->myInlineFunction() ;
Case 2: Assign the result of this function to a variable and use it for subsequent accesses
var = mobj->myInlineFunction() ;
Which one should be preferred??
Case 2 can give you a lot of performance, if the function does something that takes some time.
Choose it if
you do not need side effects of the function to happen
the function would always the return the same result in that context
The decision on whether to hold onto a return value or to recall the function again, should not be based on whether the function is inlined or not - as this is an implementation detail that may change over the lifetime/evolution of the class. As a rule of thumb I would always hang onto the return value if it does not make the code too complicated, as you do not know as a user of a class, what the cost of the function is - and what is cheap today could be expensive tomorrow. So I would go with Case 2.
I would use Case 2 even if performance is not a problem. If all you care is the result of this function, then assigning it to a variable allows you later to easily switch to another method of obtaining this result.
If the function returns the same result for every call, you have to use case 2 as it does not make sense to use case 1 even if it is inline function
I can not understand the relation between inlining the function and assigning it to a function pointer as I understand.
But for sure, the first way is self-documenting.
EDIT ::
Thanks Ahmed,
It depends actually and one can not always be used instead of the other way.
Again, the first way is clearer for me at least, if both work.
Unfortunatly there isn't one simple answer, it depends on the function.
If the function is trivial, something like { return 6; }, just call it each time. The compiler will inline the call and remove the code. You should find no difference between assigning it to a variable, or not.
If the function is more complex, then it might be worth assigning it to a variable. Is the value constant throughout the program? Then maybe add to the class a static member which contains the value?
Optimizing without knowing what or where usually ends up with more complex code that is not faster than the original.
To me the criteria to determine what solution to use is not based in the information that you provide.
If the method is an accessor (just returns an internal value, as in std::vector<>::size() ) then make it inline and do not cache the result.
If the method does perform significant work, don't make it inline and measure (you cannot measure an inlined method) how many times it is called, what cost it represents. Then decide if caching or inlining is apropriate.
Caching the result (your case 2) can be an improvement for expensive methods, but only if the value is guaranteed not to change between the uses, and in this case I would not make the method inlined.
You must cache the result if if affects your algorithm negatively (create memory based on the result and then use that memory checking overruns with that same result, if the value changes you will overrun your buffer)