STL provides binary search functions std::lower_bound and std::upper_bound,
but I tend not to use them because I\'ve been unable to remember what they do,
because their contract
Imagine what you would do if you want to find the first element equal to val in [first, last). You first exclude from first elements which are strictly smaller than val, then exclude backward from last - 1 those strictly greater than val. Then the remaining range is [lower_bound, upper_bound]