#c #lambda #c 17 #function-templates-overloading
Вопрос:
Как я должен изменить свою текущую сигнатуру функции
templatelt;class TypeData,typename TypeFunc1 = Identity,typename TypeFunc2gt; bool isPrime(const TypeDataamp; n,TypeFunc1 calcSqrt = {},TypeFunc2 isDivisible = [](const TypeDataamp; a,const TypeDataamp; b) {return a%b==0;},const bool debug = false)
для того, чтобы быть вызванным из
auto fSqrt = [](decltype(n) v) {return std::sqrt(static_castlt;floatgt;(v));}; std::coutlt;lt;(isPrime(n,fSqrt)?"Positive":"Negative")lt;lt;'n';
Visual Studio 2019 дает
C2783 ‘bool isPrime(const TypeData amp;,TypeFunc1,TypeFunc2,const bool)’: не удалось вывести аргумент шаблона для ‘TypeFunc2’
Хотя и без этого все прекрасно TypeFunc2 isDivisible = [](const TypeDataamp; a,const TypeDataamp; b) {return a%b==0;}
.
Каков правильный синтаксис для передачи лямбды по умолчанию?
Пожалуйста, помогите мне, пожалуйста.
Комментарии:
1. Если один параметр шаблона имеет аргумент по умолчанию, то все параметры, следующие за ним, также должны иметь аргументы по умолчанию.
Ответ №1:
Проблема в том, что аргументы по умолчанию не способствуют вычету типов в параметрах шаблона.
Это можно показать на этом основном примере:
template lt;typename Xgt; void f(X a = 2); int main() { f(); // The compiler spits out an error since it cannot determine the type 'X' holds }
Что вам нужно будет сделать в этом сценарии, так это вместо этого использовать перегрузку функций:
// ... templatelt;class TypeData, typename TypeFunc1, typename TypeFunc2gt; bool isPrime(const TypeDataamp; n, TypeFunc1 calcSqrt, TypeFunc2 isDivisible, const bool debug); templatelt;class TypeDatagt; bool isPrime(const TypeDataamp; n) { return isPrime(n, Identity{}, [](const TypeDataamp; a, const TypeDataamp; b) { return a % b == 0; }, false); } // ...
Ответ №2:
Ответ Рукса на самом деле очень хорош. Другой вариант-использовать функцию std::, она также может соответствовать вашим потребностям:
templatelt;class TypeData,typename TypeFunc1=Identity,typename TypeFunc2 = std::functionlt;bool(const TypeDataamp;, const TypeDataamp;)gt;gt; bool isPrime( const TypeDataamp; n, TypeFunc1 calcSqrt = {}, TypeFunc2 isDivisible = [](const TypeDataamp; a,const TypeDataamp; b) {return a%b==0;}, const bool debug = false);
Ответ №3:
Вам необходимо добавить тип по умолчанию для вашего TypeFunc2
, например:
templatelt;class TypeData, typename TypeFunc1 = Identity, typename TypeFunc2 = bool(*)(const TypeDataamp;,const TypeDataamp;)gt; //^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ bool isPrime(const TypeDataamp; n, TypeFunc1 calcSqrt = {}, TypeFunc2 isDivisible = [](const TypeDataamp; a,const TypeDataamp; b) {return a%b==0;}, const bool debug = false) { // ... }