๐ŸŽ“ A1Learner
๐Ÿ”
0 of 34 lessons completed

C++ Generic Lambdas

A generic lambda is a lambda with an auto parameter. The compiler makes the lambda work for each type it is called with.

One lambda for three types

The show lambda takes an auto parameter. It prints an int, a double and a string in three calls.

#include <iostream>
#include <string>

int main() {
  auto show = [](auto value) {
    std::cout << value << "\n";
  };
  show(42);
  show(3.5);
  show(std::string("hello"));
  return 0;
}

A generic lambda inside transform

The doubler lambda works on a vector of ints first. The same lambda then works on a vector of doubles.

#include <algorithm>
#include <iostream>
#include <vector>

int main() {
  auto doubler = [](auto number) {
    return number * 2;
  };
  std::vector<int> ints = {1, 2, 3};
  std::vector<int> doubledInts(3);
  std::transform(ints.begin(), ints.end(), doubledInts.begin(), doubler);
  std::cout << "Ints:";
  for (int value : doubledInts) {
    std::cout << " " << value;
  }
  std::cout << "\n";
  std::vector<double> doubles = {0.5, 1.5, 2.5};
  std::vector<double> doubledDoubles(3);
  std::transform(doubles.begin(), doubles.end(), doubledDoubles.begin(), doubler);
  std::cout << "Doubles:";
  for (double value : doubledDoubles) {
    std::cout << " " << value;
  }
  std::cout << "\n";
  return 0;
}

Sorting words with a generic lambda

The sort comparison is a generic lambda here. It reads the length of each word it is given.

#include <algorithm>
#include <iostream>
#include <string>
#include <vector>

int main() {
  std::vector<std::string> words = {"strawberry", "fig", "banana", "pear"};
  auto byLength = [](auto a, auto b) {
    return a.size() < b.size();
  };
  std::sort(words.begin(), words.end(), byLength);
  for (const std::string& word : words) {
    std::cout << word << "\n";
  }
  return 0;
}

Example

#include <iostream>
#include <string>

int main() {
  auto show = [](auto label, auto value) {
    std::cout << label << ": " << value << "\n";
  };
  show(std::string("Count"), 7);
  show(std::string("Price"), 9.5);
  show(std::string("Name"), std::string("Mina"));
  return 0;
}

Key points

  • An auto parameter leaves the parameter type open.
  • The compiler builds a version of the lambda for each called type.
  • The body must work for every type the lambda is called with.
  • A generic lambda can return different types for different calls.
  • Algorithms accept generic lambdas like any other lambda.
  • One generic lambda can replace several typed copies of the same body.

In this example, one show lambda prints labelled values of three types. Both parameters are auto parameters. Each call fixes its own pair of types.

Try it Yourself

Edit the code, then press Run.

Running is simulated

Exercise

What makes a lambda generic?