Had you invested in low-cost index funds instead of doing what you did, would you have more or less? How much more or less?
GreaterThanZero.com


Page 8 of: C++ auto and decltype Explained, by Thomas Becker   about me  

An Example to Put You on Guard

Taking our cue from one of the examples of the previous section, let us assume that we're working on some numerical computations using floating point arithmetic, and we frequently need the min and max of two numbers that may come in as different types, such as int and double. This precludes the direct use of std::min, since the latter requires its arguments to be of the same type:
int i = 42;
double d = 42.1;
auto a = std::min(i, d); // error: ambiguous template parameter
If we wanted to use std::min, we would have to write
auto a = std::min(static_cast<double>(i), d);

This gets old pretty quickly, especially in a day and age where we want even our C++ code to look like Python. So rather naturally, we would want a version of min and max that deals with the different types.

In 2001, Andrei Alexandrescu wrote an article on implementing min and max in C++, responding to a challenge posed by Scott Meyers. If you have read the article, or any one of the related discussions on the Web that have happened since, then you know that going for full-blown generic versions of mixed-type min and max functions is not a good idea. Instead, we should aim for something that is meant to be used for our specific purpose only. We probably already have a bunch of utilities in a namespace called something like floating_point_utilities. Now we want to put functions fpmin and fpmax in there that allow us to write
using namespace floating_point_utilities;
auto a = fpmin(i, d);

Since the new functions are in our own namespace, we could of course call them min and max. Personally, I prefer to give things unique names whenever possible so I can use using namespace liberally. Also, the names fpmin and fpmax are a good reminder of the specific purpose of these functions.

The generic functions min and max take their arguments by const reference. That's because being generic, they must be concerned with the cost of copying large objects. For our fpmin and fpmax, that is not a consideration. Moreover, taking arguments by const double& and const int& would look odd in a world of numerical functions, where arguments are always taken by value. Therefore, we let our fpmin and fpmax take their arguments by value until the profiler tells us otherwise, which is not likely to happen.

All this being said, how hard can it be to write those little three-liners? Very hard. If you're not on your toes about the subtleties of decltype, you may end up writing the following, and you would not be the first one to do so:
<horrible>
template<typename T, typename S>
auto fpmin(T x, S y) -> decltype(x < y ? x : y) {
  return x < y ? x : y;
}
</horrible>
According to our discussion in the previous section, the type
decltype(x < y ? x : y)
may or may not be a reference. If the types of T and S are the same, then it is a reference. If they are a mixture like int and double, it is not. In the former case, our fpmin function as defined above returns a reference to a local variable (a parameter in this case). You will probably agree that returning a reference to a local variable or a temporary ranks high among the worst and most embarrassing things a C++ programmer can do. Depending on the circumstances, it may or may not be caught via a compiler warning. Here's the correct version of fpmin:
// Min function intended for basic numeric types. The arguments
// may be of different type, in which case the one with lower
// precision gets promoted.
//
template<typename T, typename S>
auto fpmin(T x, S y) ->
  typename std::remove_reference<decltype(x < y ? x : y)>::type {
  return x < y ? x : y;
}
Now is a good time to tell you, as I promised earlier, why I am not a big fan of the use of the lexical token auto in the trailing return type syntax, as seen above on our fpmin function. As we know by now, the way that the other auto, the one that is used when declaring and initializing a variable, deduces the type of an expression is substantially different from the way decltype works. In the context of trailing return type syntax, only decltype matters. Perhaps I'm overly sensitive, but the use of the lexical token auto in this context leads my mind astray, towards the reference-dropping semantics of the other auto. That mental association is dangerous, as evidenced by the fpmin example.