Professional C__ - Marc Gregoire [276]
Chapter 16
Additional Library Utilities
WHAT’S IN THIS CHAPTER
How you can use std::function for function pointers
How to work with compile time rational numbers
How to work with time
How to generate random numbers
What tuples are and how to use them
C++11 adds a lot more functionality to the C++ standard library not described in previous chapters. These additional library features are combined and explained in this chapter because they don’t fit anywhere else.
STD::FUNCTION
std::function R is the return value type of the function and ArgTypes is a comma-separated list of argument types for the function. The following example demonstrates how to use std::function to implement a function pointer. It creates a function pointer f1 to point to the function func(). Once f1 is defined, you can call func() by using the name func or f1: void func(int num, const string& str) { cout << "func(" << num << ", " << str << ")" << endl; } int main() { function f1(1, "test"); return 0; } Code snippet from Function\function.cpp Of course, in the preceding example it is possible to use the C++11 auto keyword, which removes the need for you to specify the exact type of f1. The following works exactly the same and is much shorter: auto f1 = func; Code snippet from Function\function.cpp Since std::function types behave as function pointers, they can be passed to STL algorithms as shown in the following example using the count_if() algorithm. STL algorithms are discussed in Chapter 13. bool isEven(int num) { return num % 2 == 0; } int main() { vector for (int i = 0; i < 10; ++i) vec.push_back(i); auto f2 = isEven; // f2 will be of type function int cnt = count_if(vec.cbegin(), vec.cend(), f2); cout << cnt << " even numbers" << endl; return 0; } Code snippet from Function\function_count_if.cpp After the preceding examples, you might think that std::function is not really useful; but, where std::function really shines, is accepting a function pointer as argument to your own function. The following example defines a function called process(), which accepts a reference to a vector and a std::function. The process() function will iterate over all the elements in the given vector and will call the given function f for each element. You can think of the parameter f as a callback. The print() function prints a given element to the console. The main() function first creates a vector of integers and populates it. It then calls the process() function with a function pointer to print(). The result will be that each element in the vector is printed. The last part of the main() function demonstrates that you can also pass a lambda expression for the std::function parameter of the process() function, and that’s the power of std::function. You cannot get this same functionality by using a function pointer typedef. void process(const vector { for (auto& i : vec) f(i); } void print(int num) { cout << num << " "; } int main() { vector for (int i = 0; i < 10; ++i) vec.push_back(i); process(vec, print); cout << endl; int sum = 0; process(vec, [&sum](int num){sum += num;}); cout << "sum = " << sum << endl; return 0; } Code snippet from Function\function_callback.cpp The output of this example is as follows: 0 1 2 3 4 5 6 7 8 9 sum = 45 RATIOS
std::function, defined in the
The C++11 Ratio library allows you to exactly represent any finite rational number that you can use at compile time. Everything is defined