检测模板化操作符()的限定符
Detect qualifiers of templated operator()
我正在寻找一个特征来检测和提取模板化operator()
的完整签名(检查方法限定符volatile
和const
)。
表示std::bind
表达式(不使用std::is_bind_expression
)和带有自动参数的lambda。预期的返回类型和参数是已知的。
例如:
template<typename Fn, typename T>
struct is_templated_functor { ... };
auto fun = [](auto) mutable { };
using ty = decltype(&decltype(fun)::operator()<int>);
// ty = void(decltype(fun)::*)(int)
// lambda is mutable ~~~~~~~~~~~~~~~^^^^^^
is_templated_functor<void(int), decltype(fun)>::value == true;
auto fun2 = std::bind([](int) { });
using ty2 = decltype(&decltype(fun2)::operator()<int>);
// ty2 = void(decltype(fun2)::*)(int) const
is_templated_functor<void(int), decltype(fun2)>::value == true;
由于@Yakk的评论,我意识到我不需要获得表达式的完整签名来检查表达式是否可以使用const
和/或volatile
限定符调用,因为返回类型和参数已经已知。
可以使用检测组来检查具有模板化operator()
的对象是否可以用给定的限定符调用:
template<typename Fn>
struct impl_is_callable_with_qualifiers;
template<typename ReturnType, typename... Args>
struct impl_is_callable_with_qualifiers<ReturnType(Args...)>
{
template<typename T>
static auto test(int)
-> typename std::is_convertible<
decltype(std::declval<T&>()(std::declval<Args>()...)),
ReturnType
>;
template<typename T>
static auto test(...)
-> std::false_type;
};
template<bool Condition, typename T>
using add_const_if_t = typename std::conditional<
Condition,
typename std::add_const<T>::type,
T
>::type;
template<bool Condition, typename T>
using add_volatile_if_t = typename std::conditional<
Condition,
typename std::add_volatile<T>::type,
T
>::type;
template<typename T, typename Fn, bool Constant, bool Volatile>
using is_callable_with_qualifiers = decltype(impl_is_callable_with_qualifiers<Fn>::template test<
add_volatile_if_t<Volatile, add_const_if_t<Constant, typename std::decay<T>::type>>
>(0));
使用例子:
struct callable
{
void huhu(int) const { }
};
auto fun = [](auto) mutable { };
static_assert(is_callable_with_qualifiers<decltype(fun), void(int), false, false>::value, "1 failed");
static_assert(!is_callable_with_qualifiers<decltype(fun), void(int), true, true>::value, "2 failed");
auto fun2 = std::bind(&callable::huhu, callable{}, std::placeholders::_1);
// std::bind isn't const correct anyway...
static_assert(is_callable_with_qualifiers<decltype(fun2), void(int), false, false>::value, "3 failed");
static_assert(is_callable_with_qualifiers<decltype(fun2), void(int), true, false>::value, "4 failed");
static_assert(!is_callable_with_qualifiers<decltype(fun2), void(int), true, true>::value, "5 failed");
相关文章:
- 使用CMake检测支持的C++标准
- 当套接字连接断开时检测C/C++Unix
- C/C++预处理器是否可以检测一些编译器选项
- WMI检测进程创建事件-c++
- 基于树莓pi的tensorflow lite量化ssd目标检测
- 下面是我为检测链接列表中的循环而制作的代码
- 落砂模拟碰撞检测C++和SFML
- 我可以检测和更改 gcc/g++ 中结构的当前数据对齐设置吗?
- 为什么C++编译器没有检测到正确声明的类?
- 检测win32服务创建和删除的最佳方法
- 正在LLVM中检测整数比较条件
- 如何在鼠标挂钩过程中检测拖动
- 位移操作和位掩码未检测到重复字符
- 检测 COFF 对象文件中C++内联符号
- qmake:检测目标位宽(32 位或 64 位)
- 增强精神解析器规则以检测语句中的特殊结尾
- Istream提取操作符:如何检测解析失败
- 任何重载操作符()的静态检测
- 检测模板化操作符()的限定符
- 检测操作符是否存在并可在c++中调用(考虑static_assertions)