I would like to give a simple tutorial on Fold Expression, a feature in C++17 . A fold expression reduces a parameter pack to a binary operator.
A template parameter pack is a template parameter that accepts zero or more template arguments (non-types, types, or templates). A function parameter pack is a function parameter that accepts zero or more function arguments.
Syntax
- Unary Right Fold
- Unary Left Fold
- Binary Right Fold
- Binary Left Fold
Summation to add all the arguments with a simple return statement as shown in Summation function below. Arguments printed using fold expression. An example illustrated as follows:
#include <iostream>
#include <string>
#include <utility>
using namespace std;
template<typename ... T>
auto Summation(T ... t)
{
return (t + ...);
}
template<typename ...Args>
void FoldCout(Args&&... args) {
(cout << ... << (args)) << '\n';
}
int main()
{
std::cout << Summation(110, -100,5,5.66,7) << std::endl;
FoldCout("The stock price changes every moment by ", 0.5," dollars" );
getchar();
}
//Output : 27.66
//The stock price changes every moment by 0.5 dollars
Use of parenthesis to indicate precedence . An example shown in cppreference:
template<typename ...Args>
int sum(Args&&... args) {
// return (args + ... + 1 * 2); // Error: operator with precedence below cast
return (args + ... + (1 * 2)); // OK
}
The parameter pack is of length 0 the following happens.
Logical AND | value is true |
Logical OR | value is false |
Comma operator | value is void() |
A vector pushed at a time using the fold expression as follows:
#include <iostream>
#include <string>
#include <utility>
#include <vector>
using namespace std;
template<typename T, typename... Args>
void push_back_vec(std::vector<T>& v, Args&&... args)
{
static_assert((std::is_constructible_v<T, Args&&> && ...));
(v.push_back(std::forward<Args>(args)), ...);
}
int main()
{
std::vector<string> v;
push_back_vec(v, "the", "quick", "brown","fox");
push_back_vec(v,"jumps on","a","lazy","dog");
for (auto i : v) std::cout << i << ' ';
getchar();
}