Efficiency of std::bind vs lambda - c++

I have searched around a bit and found many examples and discussions of cases where you would use std::bind instead of a lambda, but the burning question I have is whether or not there is any performance benefit to one over the other. I will describe my use case:
I have a generic A* I have implemented, to which I pass successor, heuristic distance, and move cost functions.
Here is an example of my heuristic function ready to be passed off for a search (in both forms):
std::function<float(const Location*, const Location*)> hdist = std::bind(&TerrainMap::straightLineDist, this, std::placeholders::_1, std::placeholders::_2);
std::function<float(const Location*, const Location*)> hdist2 = [this](const Location* a, const Location* b){
return straightLineDist(a,b);
};
Is there any difference in the performance of these approaches? I realize the difference is probably negligible but I am curious enough to want to know.

Is there any difference in the performance of these approaches?
Perhaps, perhaps not; as commenters suggest - profile to check, or look at the assemby code you get (e.g. using the GodBolt Compiler Explorer). But you're asking the wrong question, for two main reasons:
You should probably not be passing lambda's, nor bind() results, around in the part of your code that's performance-critical.
You should definitely avoid invoking arbitrary functions via function pointer or std::function variables in performance-critical areas of your code (except if this can be de-virtualized and inlined by the compiler).
and one mind reason:
Lambdas (and std::bind()'s) are usable, and useful, without being wrapped in std::function; this wrapper has its own performance penalty, so you would only be comparing one way of using these constructs.
Bottom line recommendation: Just use Lambdas. They're cleaner, easier to understand, cheaper to compile, and more flexible syntactically. So don't worry and be happy :-) . And in performance-critical code, either use Lambda's without std::function, or don't use any of the two.

Related

Are there any more useful use-cases of functors?

I am trying to understand cases that require using functors. Most of the answer on Stackoverflow and other websites put emphasis on being able to define different adders or multipliers regarding benefits of functors.
Can the use of functors go beyond them? What are some other uses of functors?
More often than not, functors are used with other API calls that need some kind of function object. For example, sorting vectors of user-defined objects which don't have operator() or operator< (etc.) defined.
There are some cases where a set of functors may prove useful. One such case comes when you have several algorithms which functionally do the same thing, but achieve varying levels of accuracy. This happens a lot with some numeric optimization problems: given the general form of a matrix, we might use a different technique to find the solution of a linear equation (e.g., sparse vs dense problem-matracies can employ different algorithms to invert the matrix).
In particular, you should consider functors versus lambdas. In modern versions of C++, there really isn't a need to specify a functor unless you're implementing a function/method that needs a functor (or lambda) as an argument. There are some cases to consider: Do you need a unit-test? Is the functor itself a prototype of future functionality? etc.
ADDENDUM: The key thing to consider is that the use of functor/lambda ultimately boils down to a design decision. As #t.niese noted in the comments, you could use just use functions in combination of template arguments. In addition to the previous considerations above, consider whether or not you can make a compile-time or run-time assessment of the needed functionality.
Additionally, as you make design decisions, you may want to consider "Is there a need for this function to be used outside of this specific context?" If the answer is no, that's a compelling argument to choose a lambda over a free function. With regards to functor specifically, this was an important pattern added before the addition of lambdas to the standard. Typically they're defined in a somewhat private context (frequently in the implementation files, thus after compiled into a library, obfuscated to users of the API). Now with lambdas, you can simply define them within another function or even as a function argument, instead of pre-defining them prior to need.

Any reason to not use auto& for C++ range-based for-loops?

For example, the loop:
std::vector<int> vec;
...
for (auto& c : vec) { ... }
will iterate over vec and copy each element by reference.
Would there ever be a reason to do this?
for (int& c : vec) { ... }
The two code snippets will result in the same code being generated: with auto, the compiler will figure out that the underlying type is int, and do exactly the same thing.
However, the option with auto is more "future-proof": if at some later date you decide that int should be replaced with, say, uint8_t to save space, you wouldn't need to go through your code looking for references to the underlying type that may need to be changed, because the compiler will do it for you automatically.
Use auto wherever it makes the code better, but nowhere else. Understand the impact using auto overly-liberally has on maintainability.
The question here really is if there is any reason why you shouldn't use auto for anything you can.
Well, let's get one thing out of the way first of all. The fundamental reason why auto was introduced in the first place was two-fold.
First, it makes declarations of complex-type variables simpler and easier to read and understand. This is especially true when declaring an iterator in a for loop. Consider the C++03 psudocode:
for (std::vector <Foo>::const_iterator it = myFoos.begin(); it != myFoos.end(); ++it)
This can become much more complex as the complexity of myFoos's type becomes more complex. Moreover if the type of myFoos is changed in a subtle way, but in a way that's insignifigant to the loop just written, the complex declaration must be revisited. This is a maintennance problem made simpler in C++11:
for (auto it = myFoos.begin(); it != myFoos.end(); ++it)
Second, there are situations which arise that are impossible to deal with without the facilities provided by auto and it's sibling, decltype. This comes up in templates. Consider (source):
template<typename T, typename S>
void foo(T lhs, S rhs) {
auto prod = lhs * rhs;
//...
}
In C++03 the type of prod cannot always be inferred if the types of lhs and rhs are not the same. In C++11 this is possible using auto. Alas it is also possible using decltype, but this was also added to C++11 along with auto.
Many of the C++ elite suggest that you should use auto anywhere possible. The reason for this was stated by Herb Sutter in a recent conference:
It's shorter. It's more convinient. It's more future-proof, because
if you change your function's return type, auto just works.
However they also acknowledge the "sharp edges." There are many cases where auto doesn't do what you want or expect. These sharp edges can cut you when you want a type conversion.
So on the one hand we have a highly respected camp telling us "use auto everywhere possible, but nowhere else." This doesn't feel right to me however. Most of the benefits that auto provide are provided at what I'm going to call "first-write time." The time when you are first writing a piece of code. As you're writing a big chink of brand-new code you can go ahead and use auto virtually everywhere and get exactly the behavior you expect. As you're writing the code you know exactly what's going on with your types and variables. I don't know about you, but as I write code there is a constant stream of thoughts going through my head. How do I want to create this loop? What kind of thing do I want that function to return so I can use it here? How can I write this so that is fast, correct, and easy to understand 6 months from now? Most of this is never expressed directly in the code that I write, except that the code that I write is a direct result of these thoughts.
At that time, using auto would make writing this code simpler and easier. I don't have to burden my mind with all the little minute of signed versus unsigned, reference vs value, 32 bit vs 64 bit, etc. I just write auto and everything works.
But here's my problem with auto. 6 months later when revisiting this code to add some major new functionality, that buzz of thought that was going through my mind as I first write the code has long been extinguished. My buffers were flushed long ago, and none of those thought are with me anymore. If I have done my job well, then the essence of those thoughts are expressed directly in the code I wrote. I can reverse-engineer what I was thinking by just looking at the structure of my functions and data types.
If auto is sprinkled everywhere, a big part of that cognizance is lost. I don't know what I was thinking would happen with this datatype because now it's inferred. If there was a subtle relationship taking place with an operator, that relationship is no longer expressed by the datatypes -- it's all just auto.
Maintenance becomes more difficult because no I have to re-create much of that thought. Subtle relationships become more clouded, and everything is just harder to understand.
So I'm not a fan of using auto everywhere possible. I think that makes maintenance harder than it has to be. That's not to say I believe that auto should only be used where it's required. Rather, it's a balancing act. The four criteria I use to judge the quality of my (or anyone's code) are: efficiency, correctness, robustness, and maintainability. In no particular order. If we design a spectrum of auto use where one side is "purely optional" and the other side is "strictly required", I feel that in general the closer to "purely optional" we get, the more maintainability suffers.
All this to say, finally, that my philosophy can be nutshelled as:
Use auto wherever it makes the code better, but nowhere else.
Understand the impact using auto overly-liberally has on
maintainability.
That depends on what you want to do with c:
You want to work with copies? Use auto c
You want to work with original items and possibly modify them? Use auto& c
You want to work with original items and not modify them? Use const auto& c
There are two conflicting insterests here. On the one side, it is just simpler to type auto& everywhere than figuring the exact type en each loop. Some people will claim that it is also more future-proof if the type stored in the container changes in the future --I don't particularly agree, I'd rather have the compiler complain* and let me figure out if the assumptions made in the loop about the type still hold.
On the other side, by using auto& (instead of the more explicit int&) you are hiding the type from the reader. The maintainer reading the code will have to think what auto means in this particular context, while int clearly has a single meaning. The same people, or at least a subset of them, will claim that you don't need to think, that the IDE will tell you the type if you hover the mouse over the variable... but I don't use an IDE nor particularly like the mouse...
Over all, this is mainly a matter of style. I prefer to see the types in the code rather than have the compiler infer them for me, as I find it easier to understand when I go back to the code some time later. But for quick coding when I don't envision having to maintain this code a week from now auto is more than sufficient.
* This assumes that you use a standard compliant compiler of which VisualStudio is not an example. The assumption is that if the type is wrong, a non-const reference won't bind to the value returned by dereferencing the iterator. In VS, the compiler will gladly convert types and bind a non-const reference to the rvalue! Maybe this is why Sutter, comming from the VS world suggests using auto everywhere!
I agree with dasblinkenlight's answer, but since you are asking when int& is better than auto&, I can paraphrase it this way:
Use int& when you would like your code to break if/when someone decides to change the type of your vector.
For example: your vectors usually contain int16_t, but this particular one requires greater precision (assuming int has 32-bit or greater precision). You don't want someone to change the type from int to int16_t and get a program that contains a silent overflow in calculations.
Another example: your code looks like this:
namespace joes_lib
{
int frobnicate(int);
}
for (int& c : vec) { c = frobnicate(c); }
Here, if someone changes vec to something like vector<int16_t> or, worse, vector<unsigned>, auto will silently succeed and lead to loss of precision in joe's library function. Compiler may or may not generate warnings about this.
These examples look clumsy and obscure, so you may want to comment such usage of non-auto types in loops.

Should we use constexpr everywhere we can?

We obviously can't make everything constexpr. And if we don't make anything constexpr, well, there won't be any big problems. Lots of code have been written without it so far.
But is it a good idea to slap constexpr in anything that can possibly have it? Is there any potential problem with this?
It won't bother the compiler. The compiler will (or should anyway) give you a diagnostic when/if you use it on code that doesn't fit the requirements of a constexpr.
At the same time, I'd be a bit hesitant to just slap it on there because you could. Even though it doesn't/won't bother the compiler, your primary audience is other people reading the code. At least IMO, you should use constexpr to convey a fairly specific meaning to them, and just slapping it on other expressions because you can will be misleading. I think it would be fair for a reader to wonder what was going on with a function that's marked as a constexpr, but only used as a normal run-time function.
At the same time, if you have a function that you honestly expect to use at compile time, and you just haven't used it that way yet, marking it as constexpr might make considerably more sense.
Why I don't bother to try and put constexpr at every opportunity in list form, and in no particular order:
I don't write one-liner functions that often
when I write a one-liner it usually delegates to a non-constexpr function (e.g. std::get has come up several times recently)
the types they operate on aren't always literal types; yes, references are literal types, but if the referred type is not literal itself I can't really have any instance at compile-time anyway
the type they return aren't always literal
they simply are not all useful or even meaningful at compile-time in terms of their semantics
I like separating implementation from declaration
Constexpr functions have so many restrictions that they are a niche for special use only. Not an optimization, or a desirable super-set of functions in general. When I do write one, it's often because a metafunction or a regular function alone wouldn't have cut it and I have a special mindset for it. Constexpr functions don't taste like other functions.
I don't have a particular opinion or advice on constexpr constructors because I'm not sure I can fully wrap my mind around them and user-defined literals aren't yet available.
I tend to agree with Scott Meyers on this (as for most things): "Use constexpr whenever possible" (from Item 15 of Effective Modern C++), particularly if you are providing an API for others to use. It can be really disappointing when you wish to perform a compile-time initialization using a function, but can't because the library did not declare it constexpr. Furthermore, all classes and functions are part of an API, whether used by the world or just your team. So use it whenever you can, to widen its scope of usage.
// Free cup of coffee to the API author, for using constexpr
// on Rect3 ctor, Point3 ctor, and Point3::operator*
constexpr Rect3 IdealSensorBounds = Rect3(Point3::Zero, MaxSensorRange * 0.8);
That said, constexpr is part of the interface, so if the interface does not naturally fit something that can be constexpr, don't commit to it, lest you have to break the API later. That is, don't commit constexpr to the interface just because the current, only implementation can handle it.
Yes. I believe putting such constness is always a good practice wherever you can. For example in your class if a given method is not modifying any member then you always tend to put a const keyword in the end.
Apart from the language aspect, mentioning constness is also a good indication to the future programmer / reviewer that the expression is having const-ness within that region. It relates to good coding practice and adds to readability also. e.g. (from #Luc)
constexpr int& f(int& i) { return get(i); }
Now putting constexpr suggests that get() must also be a constexpr.
I don't see any problem or implication due constexpr.
Edit: There is an added advantage of constexpr is that you can use them as template argument in some situations.

Large scale usage of Meyer's advice to prefer Non-member,non-friend functions?

For some time I've been designing my class interfaces to be minimal, preferring namespace-wrapped non-member functions over member functions. Essentially following Scott Meyer's advice in the article How Non-Member Functions Improve Encapsulation.
I've been doing this with good effect in a few small scale projects, but I'm wondering how well it works on a larger scale. Are there any large, well regarded open-source C++ projects that I can take a look at and perhaps reference where this advice is strongly followed?
Update: Thanks for all the input, but I'm not really interested in opinion so much as finding out how well it works in practice on a larger scale. Nick's answer is closest in this regard, but I'd like to be able to see the code. Any sort of detailed description of practical experiences (positives, negatives, practical considerations, etc) would be acceptable as well.
I do this quite a bit on the project I work on; the largest of which at my current company is around 2M lines, but it's not open source, so I can't provide it as a reference. However, I will say that I agree with the advice, generally speaking. The more you can separate the functionality which is not strictly contained to just one object from that object, the better your design will be.
By way of an example, consider the classic polymorphism example: a Shape base class with subclasses, and a virtual Draw() function. In the real world, Draw() would need to take some drawing context, and potentially be aware of the state of other things being drawn, or the application in general. Once you put all that into each subclass implementation of Draw(), you're likely to have some code overlap, or most of your actual Draw() logic will be in the base class, or somewhere else. Then consider that if you want to re-use some of that code, you'll need to provide more entry points into the interface, and possibly pollute the functions with other code not related to drawing shapes (eg: multi-shape drawing correlation logic). Before long, it'll be a mess, and you'll wish you had a draw function which took a Shape (and context, and other data) instead, and Shape just had functions/data which were entirely encapsulated and not using or referencing external objects.
Anyway, that's my experience/advice, for what it's worth.
I'd argue that the benefit of non-member functions increases as the size of the project increases. The standard library containers, iterators, and algorithms library are proof of this.
If you can decouple algorithms from data structures (or, to phrase it another way, if you can decouple what you do with objects from how their internal state is manipulated), you can decrease coupling between your classes and take greater advantage of generic code.
Scott Meyers isn't the only author who has argued in favor of this principle; Herb Sutter has too, especially in Monoliths Unstrung, which ends with the guideline:
Where possible, prefer writing functions as nonmember nonfriends.
I think one of the best examples of an unneccessary member function from that article is std::basic_string::find; there is no reason for it to exist, really, as std::find provides exactly the same functionality.
OpenCV library does this. They have a cv::Mat class that presents a 3D matrix (or images). Then they have all the other functions in the cv namespace.
OpenCV library is huge and is widely regarded in its field.
One practical advantage of writing functions as nonmember nonfriends is that doing so can significantly reduce the time it takes to thoroughly test and verify the code.
Consider, for example, the sequence container member functions insert and push_back. There are at least two approaches to implementing push_back:
It can simply call insert (it's behavior is defined in terms of insert anyway)
It can do all the work that insert would do (possibly calling private helper functions) without actually calling insert
Obviously, when implementing a sequence container, you probably want to use the first approach. push_back is just a special form of insert and (to the best of my knowledge) you can't really get any performance benefit by implementing push_back some other way (at least not for list, deque, or vector).
However, to thoroughly test such a container, you have to test push_back separately: since push_back is a member function, it can modify any and all of the internal state of the container. From a testing standpoint, you should (must?) assume that push_back is implemented using the second approach because it is possible that it could be implemented using the second approach. There is no guarantee that it is implemented in terms of insert.
If push_back is implemented as a nonmember nonfriend, it can't touch any of the internal state of the container; it must use the first approach. When you write tests for it, you know that it can't break the internal state of the container (assuming the actual container member functions are implemented correctly). You can use that knowledge to significantly reduce the number of tests that you need to write to fully exercise the code.
(I don't have time to write this up nicely, the following's a 5 minute brain dump which doubtless can be ripped apart at various trival levels, but please address the concepts and general thrust.)
I have considerable sympathy for the position taken by Jonathan Grynspan, but want to say a bit more about it than can reasonably be done in comments.
First - a "well said" to Alf Steinbach, who chipped in with "It's only over-simplified caricatures of their viewpoints that might seem to be in conflict. For what it's worth I don't agree with Scott Meyers on this matter; as I see it he's over-generalizing here, or he was."
Scott, Herb etc. were making these points when few people understood the trade-offs or alternatives, and they did so with disproportionate strength. Some nagging hassles people had during evolution of code were analysed and a new design approach addressing those issues was rationally derived. Let's return to the question of whether there were downsides later, but first - worth saying that the pain in question was typically small and infrequent: non-member functions are just one small aspect of designing reusable code, and in enterprise scale systems I've worked on simply writing the same kind of code you'd have put into a member function as a non-member is rarely enough to make the non-members reusable. It's pretty rare for them to even express algorithms that are both complex enough to be worth reusing and yet not tightly bound to the specific of the class they were designed for, that being weird enough that it's practically inconceivable some other class will happen along supporting the same operations and semantics. Often, you also need to template arguments, or introduce a base class to abstract the set of operations required. Both have significant implications in terms of performance, being inline vs out-of-line, client-code recompilation.
That said, there's often less code changes and impact study required when changing implementation if operations have been implementing in terms of a public interface, and being a non-friend non-member systematically enforces that. Occasionally though, it makes the initial implementation more verbose or in some other way less desirable and maintainble.
But, as a litmus test - how many of these non-member functions sit in the same header as the only class for which they're currently applicable? How many want to abstract their arguments via templates (which means inlining, compilation dependencies) or base classes (virtual function overheads) to allow reuse? Both discourage people from seeing them as reusable, but when not the case, the operations available on a class are delocalised, which can frustrate developers perception of a system: the develop often has to work out for themselves the rather disappointing fact that - "oh - that will only work for class X".
Bottom line: most member functions aren't potentially reusable. Much corporate code isn't broken into clean algorithm versus data with potential for reuse of the former. That kind of division just isn't required or useful or conceivably useful 20 years down the road. It's much the same as get/set methods - they're needed at certain API boundaries, but can constitute needless verbosity when ownership and use of the code is localised.
Personally, I don't have an all or nothing approach to this, but decide what to make a member function or non-member based on whether there's any likely benefit to either, potential reusability versus locality of interface.
I also do this alot, where it seems to make sense, and it causes absolutely no problems with scaling. (although my current project is only 40000 LOC) In fact, I think it makes the code more scalable - it slims down classes, reduces dependencies.
It sometimes requires you to refactor your functions to make them independent of members of the class - and thereby often creating a library of more general helper functions, which you can easly reuse elsewhere. I'd also mention that one of the common problems with many large projects is the bloating of classes - and I think preferring non-member, non-friend functions also helps here.
Prefer non-member non-friend functions for encapsulation UNLESS you want implicit conversions to work for class templates non-member functions (in which case you better make them friend functions):
That is, if you have a class template type<T>:
template<class T>
struct type {
void friend foo(type<T> a) {}
};
and a type implicitly convertible to type<T>, e.g.:
template<class T>
struct convertible_to_type {
operator type<T>() { }
};
The following works as expected:
auto t = convertible_to_type<int>{};
foo(t); // t is converted to type<int>
However, if you make foo a non-friend function:
template<class T>
void foo(type<T> a) {}
then the following doesn't work:
auto t = convertible_to_type<int>{};
foo(t); // FAILS: cannot deduce type T for type
Since you cannot deduce T then the function foo is removed from the overload resolution set, that is: no function is found, which means that the implicit conversion does not trigger.

Should I make my functions as general as possible?

template<class T>
void swap(T &a, T &b)
{
T t;
t = a;
a = b;
b = t;
}
replace
void swap(int &a, int &b)
{
int t;
t = a;
a = b;
b = t;
}
This is the simplest example I could come up with,but there should be many other complicated functions.Should I make all methods I write templated if possible?
Any disadvantages to do this?
thanks.
Genericity has the advantage of being reusable. However, write things generic, only if:
It doesn't take much more time to do that, than do it non-generic
It doesn't complicate the code more than a non-generic solution
You know will benefit from it later
However, know your standard library. The case you presented is already in STL as std::swap.
Also, remember that when writing generically using templates, you can optimize special cases by using template specialization. However, always to it when it's needed for performance, not as you write it.
Also, note that you have the question of run-time and compile-time performance here. Template-based solutions increase compile-time. Inline solutions can but not must decrease run-time.
`Cause "Premature optimization and genericity is the root of all evil". And you can quote me on that -_-.
Reusable code is reusable only if you actually reuse it. so write the function naturally in the first instance. If a bit later you come across a situation where the code could be reused with a little tweak, go back and refactor it, It is at the refactoring stage you should consider writing template functions.
The simplest answer to your question is what many people smarter than myself have been saying for years:
Never write more than the minimum you can get away with.
Make them as generic as you can trivially make them. If it's truly trivial (such as the above example) then it takes no extra work, and might save you some work in the future
The first time you write swap you shouldn't
The second time it might be tempting but sometime you can get away without making the whole thing a mess
The third time it should be clear that you must. However depending on how many places you've used one and two it might be time consuming so the second time should be a good decision
There are disadvantages to using templates all the time. It (can) greatly increase the compilation time of your program and can make compilation errors more difficult to understand.
As taldor said, don't make your functions more generic than they need to be.
You may take a look at the function parameters and the way they are used. If all operations are done through overloaded operators the function may be very generic and a good candidate to become a template. Otherwise, the presence of very specialized class types and functions calls may make generic reusability very problematic and any eventual flexibility should be rather realized through polymorphism.
A few thoughts:
Know the STL. There is std::swap already. Instead of spending your time making everything as generic as possible, spend your time becoming more familiar with the STL.
Don't do it till you need it: "Always implement things when you actually need them, never when you just foresee that you need them."---Ron Jeffries. If you don't actually reuse the code you didn't write reusable code, you wrote unnecessary code. Unnecessary code is expensive to develop, expensive to test, and expensive to maintain. Don't forget opportunity cost!
Keep things simple: "Make everything as simple as possible, but not simpler."---Albert Einstein. This is KISS.