如果默认可构造,则默认参数
Default argument if default constructible
我有一个小问题,我的代码可以工作,但并不理想。
我有一个将谓词作为参数的函数。我想支持这些语法:
myClass.foo([](auto param){ return true; }); // predicate sent as parameter
myClass.foo<PredicateType>(); // predicate type sent as template argument
myClass.foo(); // default predicate took
但是,为了做到这一点,我复制了这样的函数:
struct MyClass {
template<typename Predicate = DefaultPredicate&&, std::enable_if_t<std::is_default_constructible<detail::decay_t<Predicate>>::value, int> = 0>
void foo(Predicate&& p = std::decay_t<Predicate>{}) {
// stuff...
}
template<typename Predicate, std::enable_if_t<!std::is_default_constructible<detail::decay_t<Predicate>>::value, int> = 0>
void foo(Predicate&& p) {
// exact same stuff...
}
};
有没有办法在不复制我的代码的情况下做到这一点?
理想的是具有一种功能。我该怎么做,最好是在 c++11 中?
只需创建一个不带参数的模板函数,然后转发给带谓词的函数:
#include <iostream>
struct Predicate {};
struct DefaultPredicate {};
struct MyClass {
template<typename Predicate>
void foo(Predicate&& p) {
std::cout << "Stuff\n";
}
template<typename Predicate = DefaultPredicate>
void foo() {
std::cout << "Forward ";
foo(Predicate{});
}
};
int main() {
MyClass my;
my.foo<>(); // DefaultPredicate
my.foo<DefaultPredicate>();
my.foo<Predicate>();
my.foo(Predicate());
return 0;
}
去掉毫无意义的 SFINAE 和同样毫无意义的 decay
:
struct MyClass {
template<typename Predicate = DefaultPredicate>
void foo(Predicate&& p = Predicate{}) {
// stuff...
}
};
默认函数参数是单独实例化的,并且仅在实际需要时才实例化。
我有一个小问题,我的代码可以工作,但并不理想。
我有一个将谓词作为参数的函数。我想支持这些语法:
myClass.foo([](auto param){ return true; }); // predicate sent as parameter
myClass.foo<PredicateType>(); // predicate type sent as template argument
myClass.foo(); // default predicate took
但是,为了做到这一点,我复制了这样的函数:
struct MyClass {
template<typename Predicate = DefaultPredicate&&, std::enable_if_t<std::is_default_constructible<detail::decay_t<Predicate>>::value, int> = 0>
void foo(Predicate&& p = std::decay_t<Predicate>{}) {
// stuff...
}
template<typename Predicate, std::enable_if_t<!std::is_default_constructible<detail::decay_t<Predicate>>::value, int> = 0>
void foo(Predicate&& p) {
// exact same stuff...
}
};
有没有办法在不复制我的代码的情况下做到这一点? 理想的是具有一种功能。我该怎么做,最好是在 c++11 中?
只需创建一个不带参数的模板函数,然后转发给带谓词的函数:
#include <iostream>
struct Predicate {};
struct DefaultPredicate {};
struct MyClass {
template<typename Predicate>
void foo(Predicate&& p) {
std::cout << "Stuff\n";
}
template<typename Predicate = DefaultPredicate>
void foo() {
std::cout << "Forward ";
foo(Predicate{});
}
};
int main() {
MyClass my;
my.foo<>(); // DefaultPredicate
my.foo<DefaultPredicate>();
my.foo<Predicate>();
my.foo(Predicate());
return 0;
}
去掉毫无意义的 SFINAE 和同样毫无意义的 decay
:
struct MyClass {
template<typename Predicate = DefaultPredicate>
void foo(Predicate&& p = Predicate{}) {
// stuff...
}
};
默认函数参数是单独实例化的,并且仅在实际需要时才实例化。