Используйте лямбду, когда функция не подходит (для захвата локальных переменных или написания локальной функции)
Причина
Функции не могут захватывать локальные переменные или быть определены в локальной области видимости; если вам нужно это, предпочитайте лямбду там, где это возможно, и написанный вручную функциональный объект там, где нет. С другой стороны, лямбды и функциональные объекты не поддерживают перегрузку; если вам нужна перегрузка, предпочитайте функцию (обходные пути для перегрузки лямбд громоздки). Если любой вариант подходит, предпочитайте функцию; используйте простейший необходимый инструмент.
Пример
// написание функции, которая должна принимать только int или string
// -- перегрузка естественна
void f(int);
void f(const string&);
// написание функционального объекта, которому нужно захватить локальное состояние
// и который появляется в области видимости оператора или выражения -- лямбда естественна
vector<work> v = lots_of_work();
for (int tasknum = 0; tasknum < max; ++tasknum) {
pool.run([=, &v] {
/*
...
... обрабатываем (1/max)-ую часть v, tasknum-ый блок
...
*/
});
}
pool.join();
Исключение
Обобщённые лямбды предоставляют краткий способ написания шаблонов функций и могут быть полезны даже тогда, когда обычный шаблон функции справился бы с небольшим синтаксическим усложнением. Это преимущество, вероятно, исчезнет в будущем, когда все функции получат возможность иметь параметры Concept.
Контроль
- Предупреждать об использовании именованной не-обобщённой лямбды (например,
auto x = [](int i) { /*...*/; };), которая ничего не захватывает и появляется в глобальной области видимости. Вместо этого напишите обычную функцию.