Qual é a necessidade do modelo lambda introduzido em C++ 20 quando o C++ 14 já possui lambda genérico?




c++14 c++20 (3)

c ++ 14 introduziu lambdas genéricos que tornaram possível escrever o seguinte:

auto func = [](auto a, auto b){
    return a + b;
};
auto Foo = func(2, 5);
auto Bar = func("hello", "world");

É muito claro que essa func lambda genérica funciona exatamente como uma função de função func funcionaria.

Por que o comitê de C ++ decidiu adicionar a sintaxe de modelo para lamda genérica?


A nova "sintaxe de modelo familiar" para lambdas introduzida em C ++ 20 torna as construções como for_types e for_range viáveis ​​e muito mais legíveis em comparação com as alternativas para C ++ 17.

(fonte: iteração em tempo de compilação com lambdas C ++ 20 )

Outra coisa interessante que pode ser feita em lambdas genéricos C ++ 14 e C ++ 17 é chamar diretamente operator() explicitamente passando um parâmetro de modelo:

C ++ 14:

   auto l = [](auto){ };
   l.template operator()<int>(0);

C ++ 20:

  auto l = []<typename T>(){ };
  l.template operator()<int>();

O exemplo de C ++ 14 acima é bastante inútil: não há como se referir ao tipo fornecido a operator() no corpo do lambda sem dar um nome ao argumento e usando decltype . Além disso, somos obrigados a passar um argumento mesmo que não precisemos dele.

O exemplo C + + 20 mostra como T é facilmente acessível no corpo do lambda e que um lambda nulo pode agora ser arbitrariamente modelado. Isso será muito útil para a implementação das construções de tempo de compilação mencionadas anteriormente


A proposal que foi aceita em C ++ 20 tem uma longa seção de motivação, com exemplos. A premissa disso é esta:

Existem algumas razões principais pelas quais a sintaxe atual para a definição de lambdas genéricos é considerada insuficiente pelo autor. A essência disso é que algumas coisas que podem ser feitas facilmente com modelos de função normais requerem saltos significativos a serem feitos com lambdas genéricos, ou não podem ser feitas. O autor acha que lambdas são valiosos o suficiente para que o C ++ os suporte. tão bem quanto os modelos normais de função.

Depois disso, são alguns exemplos.


Como você pode usar lambdas modelados em C ++ 20, você pode restringir seus tipos de uma maneira mais fácil do que uma expressão SFINAE:

auto lambda = []<typename T>(std::vector<T> t){};

Este lambda funcionará apenas com tipos vetoriais.







generic-lambda