如何在 C++ 中有条件地编写依赖于 lambda 的 return 类型的代码?
How to conditionally write code that's dependent on lambda's return type in C++?
我有一个函数可以为它迭代的每个元素调用回调:
#include <type_traits>
#include <iostream>
using namespace std;
void iterate( const auto & on_element ) {
for ( int i = 0; i < 10; ++ i ) {
//here I want to stop iteration if function returns bool true:
if constexpr ( is_same< result_of( on_element )::type, bool >::value )
if ( ! on_element( i ) )
return;
//but when callback doesn't return bool - simply iterate the whole range:
else
on_element( i );
}
}
int main() {
const auto & stop = [&]( const int & element ) {
cout << "stop" << endl;
return false;
};
iterate( stop );
const auto & whole = [&]( const int & element ) {
cout << " " << element << endl;
};
cout << "Whole:" << endl;
iterate( whole );
}
我用 g++-10 -std=gnu++2a -fconcepts main.cpp -o main
编译它并得到这些错误:
main.cpp: In function ‘void iterate(const auto:1&)’:
main.cpp:7:69: error: wrong number of template arguments (1, should be 2)
7 | if constexpr ( is_same< result_of( on_element )::type, bool >::value )
| ^
In file included from main.cpp:1:
/usr/include/c++/10/type_traits:582:12: note: provided for ‘template<class, class> struct std::is_same’
582 | struct is_same;
| ^~~~~~~
main.cpp:7:78: error: qualified-id in declaration before ‘)’ token
7 | if constexpr ( is_same< result_of( on_element )::type, bool >::value )
| ^
main.cpp: In instantiation of ‘void iterate(const auto:1&) [with auto:1 = main()::<lambda(const int&)>]’:
main.cpp:21:20: required from here
main.cpp:8:30: error: could not convert ‘(& on_element)->main()::<lambda(const int&)>(i)’ from ‘void’ to ‘bool’
8 | if ( ! on_element( i ) )
| ~~~~~~~~~~^~~~~
| |
| void
main.cpp:8:30: error: in argument to unary !
之前我设法推理出函数 return 的值,但在这种情况下无法实现。是因为 callable 是 lambda 还是因为使用了 auto
限定词?
on_node
在您的示例中不是名称,并且 std::result_of
没有该语法(不推荐使用 std::invoke_result
)。
我想你是说
std::is_same_v<std::invoke_result_t<decltype(on_element), int>, bool>
我有一个函数可以为它迭代的每个元素调用回调:
#include <type_traits>
#include <iostream>
using namespace std;
void iterate( const auto & on_element ) {
for ( int i = 0; i < 10; ++ i ) {
//here I want to stop iteration if function returns bool true:
if constexpr ( is_same< result_of( on_element )::type, bool >::value )
if ( ! on_element( i ) )
return;
//but when callback doesn't return bool - simply iterate the whole range:
else
on_element( i );
}
}
int main() {
const auto & stop = [&]( const int & element ) {
cout << "stop" << endl;
return false;
};
iterate( stop );
const auto & whole = [&]( const int & element ) {
cout << " " << element << endl;
};
cout << "Whole:" << endl;
iterate( whole );
}
我用 g++-10 -std=gnu++2a -fconcepts main.cpp -o main
编译它并得到这些错误:
main.cpp: In function ‘void iterate(const auto:1&)’:
main.cpp:7:69: error: wrong number of template arguments (1, should be 2)
7 | if constexpr ( is_same< result_of( on_element )::type, bool >::value )
| ^
In file included from main.cpp:1:
/usr/include/c++/10/type_traits:582:12: note: provided for ‘template<class, class> struct std::is_same’
582 | struct is_same;
| ^~~~~~~
main.cpp:7:78: error: qualified-id in declaration before ‘)’ token
7 | if constexpr ( is_same< result_of( on_element )::type, bool >::value )
| ^
main.cpp: In instantiation of ‘void iterate(const auto:1&) [with auto:1 = main()::<lambda(const int&)>]’:
main.cpp:21:20: required from here
main.cpp:8:30: error: could not convert ‘(& on_element)->main()::<lambda(const int&)>(i)’ from ‘void’ to ‘bool’
8 | if ( ! on_element( i ) )
| ~~~~~~~~~~^~~~~
| |
| void
main.cpp:8:30: error: in argument to unary !
之前我设法推理出函数 return 的值,但在这种情况下无法实现。是因为 callable 是 lambda 还是因为使用了 auto
限定词?
on_node
在您的示例中不是名称,并且 std::result_of
没有该语法(不推荐使用 std::invoke_result
)。
我想你是说
std::is_same_v<std::invoke_result_t<decltype(on_element), int>, bool>