为什么 boost/etc 对模板成员函数的参数类型做这么多 SFINAE?
Why do boost/etc do so much SFINAE on template member functions' argument types?
当参数不满足各种条件时,有选择地从类接口中删除模板成员函数的理由是什么,用enable_if
等进行测试? 如果保留成员函数模板,尝试使用它们将失败,在我看来,在更复杂的情况下,编译器错误比"替换失败"更有用?
如果编译失败,那么支持这些极其严格的基于 SFINAE 的模板成员函数要求的论据是什么?
已经发现模板代码中的编译器错误 2-5 几乎无法理解。 你会得到一阵模板噪音。
SFINAE 替换失败通常会列出一个模板并说它不起作用,因为无法推断出某些参数,通常显示失败的特征。 不完美,但比模板喷出更好。
更重要的是,此类模板可以阻止其他有效的模板。
此外,如果使用类似 SFINAE 的技术,则可以测试给定方法是否存在并且在编译时有效;如果主体编译失败,则不能测试。
您觉得哪个错误消息更容易理解。这个和SFINAE?
template <class C, class = decltype(begin(std::declval<C&>())[0])>
void sort_sfinae(C& c) {
std::sort(c.begin(), c.end());
}
main.cpp: In function 'int main()':
main.cpp:11:18: error: no matching function for call to 'sort_sfinae(std::__cxx11::list<int>&)'
sort_sfinae(l);
^
main.cpp:5:6: note: candidate: template<class C, class> void sort_sfinae(C&)
void sort_sfinae(C& c) {
^
main.cpp:5:6: note: template argument deduction/substitution failed:
main.cpp:4:62: error: no match for 'operator[]' (operand types are 'std::__cxx11::list<int>::iterator {aka std::_List_iterator<int>}' and 'int')
template <class C, class = decltype(begin(std::declval<C&>())[0])>
^
<小时 />还是这个没有?
template <class C>
void sort_no_sfinae(C& c) {
std::sort(c.begin(), c.end());
}
In file included from /usr/local/include/c++/5.3.0/algorithm:62:0,
from main.cpp:2:
/usr/local/include/c++/5.3.0/bits/stl_algo.h: In instantiation of 'void std::__sort(_RandomAccessIterator, _RandomAccessIterator, _Compare) [with _RandomAccessIterator = std::_List_iterator<int>; _Compare = __gnu_cxx::__ops::_Iter_less_iter]':
/usr/local/include/c++/5.3.0/bits/stl_algo.h:4698:18: required from 'void std::sort(_RAIter, _RAIter) [with _RAIter = std::_List_iterator<int>]'
main.cpp:6:14: required from 'void sort_no_sfinae(C&) [with C = std::__cxx11::list<int>]'
main.cpp:11:21: required from here
/usr/local/include/c++/5.3.0/bits/stl_algo.h:1964:22: error: no match for 'operator-' (operand types are 'std::_List_iterator<int>' and 'std::_List_iterator<int>')
std::__lg(__last - __first) * 2,
^
In file included from /usr/local/include/c++/5.3.0/bits/stl_algobase.h:67:0,
from /usr/local/include/c++/5.3.0/list:60,
from main.cpp:1:
/usr/local/include/c++/5.3.0/bits/stl_iterator.h:328:5: note: candidate: template<class _Iterator> typename std::reverse_iterator<_Iterator>::difference_type std::operator-(const std::reverse_iterator<_Iterator>&, const std::reverse_iterator<_Iterator>&)
operator-(const reverse_iterator<_Iterator>& __x,
^
/usr/local/include/c++/5.3.0/bits/stl_iterator.h:328:5: note: template argument deduction/substitution failed:
In file included from /usr/local/include/c++/5.3.0/algorithm:62:0,
from main.cpp:2:
/usr/local/include/c++/5.3.0/bits/stl_algo.h:1964:22: note: 'std::_List_iterator<int>' is not derived from 'const std::reverse_iterator<_Iterator>'
std::__lg(__last - __first) * 2,
^
In file included from /usr/local/include/c++/5.3.0/bits/stl_algobase.h:67:0,
from /usr/local/include/c++/5.3.0/list:60,
from main.cpp:1:
/usr/local/include/c++/5.3.0/bits/stl_iterator.h:380:5: note: candidate: template<class _IteratorL, class _IteratorR> decltype ((__y.base() - __x.base())) std::operator-(const std::reverse_iterator<_Iterator>&, const std::reverse_iterator<_IteratorR>&)
operator-(const reverse_iterator<_IteratorL>& __x,
^
/usr/local/include/c++/5.3.0/bits/stl_iterator.h:380:5: note: template argument deduction/substitution failed:
In file included from /usr/local/include/c++/5.3.0/algorithm:62:0,
from main.cpp:2:
/usr/local/include/c++/5.3.0/bits/stl_algo.h:1964:22: note: 'std::_List_iterator<int>' is not derived from 'const std::reverse_iterator<_Iterator>'
std::__lg(__last - __first) * 2,
^
In file included from /usr/local/include/c++/5.3.0/bits/stl_algobase.h:67:0,
from /usr/local/include/c++/5.3.0/list:60,
from main.cpp:1:
/usr/local/include/c++/5.3.0/bits/stl_iterator.h:1138:5: note: candidate: template<class _IteratorL, class _IteratorR> decltype ((__x.base() - __y.base())) std::operator-(const std::move_iterator<_Iterator>&, const std::move_iterator<_IteratorR>&)
operator-(const move_iterator<_IteratorL>& __x,
^
/usr/local/include/c++/5.3.0/bits/stl_iterator.h:1138:5: note: template argument deduction/substitution failed:
In file included from /usr/local/include/c++/5.3.0/algorithm:62:0,
from main.cpp:2:
/usr/local/include/c++/5.3.0/bits/stl_algo.h:1964:22: note: 'std::_List_iterator<int>' is not derived from 'const std::move_iterator<_Iterator>'
std::__lg(__last - __first) * 2,
^
In file included from /usr/local/include/c++/5.3.0/bits/stl_algobase.h:67:0,
from /usr/local/include/c++/5.3.0/list:60,
from main.cpp:1:
/usr/local/include/c++/5.3.0/bits/stl_iterator.h:1145:5: note: candidate: template<class _Iterator> decltype ((__x.base() - __y.base())) std::operator-(const std::move_iterator<_Iterator>&, const std::move_iterator<_Iterator>&)
operator-(const move_iterator<_Iterator>& __x,
^
/usr/local/include/c++/5.3.0/bits/stl_iterator.h:1145:5: note: template argument deduction/substitution failed:
In file included from /usr/local/include/c++/5.3.0/algorithm:62:0,
from main.cpp:2:
/usr/local/include/c++/5.3.0/bits/stl_algo.h:1964:22: note: 'std::_List_iterator<int>' is not derived from 'const std::move_iterator<_Iterator>'
std::__lg(__last - __first) * 2,
^
In file included from /usr/local/include/c++/5.3.0/vector:65:0,
from /usr/local/include/c++/5.3.0/bits/random.h:34,
from /usr/local/include/c++/5.3.0/random:49,
from /usr/local/include/c++/5.3.0/bits/stl_algo.h:66,
from /usr/local/include/c++/5.3.0/algorithm:62,
from main.cpp:2:
/usr/local/include/c++/5.3.0/bits/stl_bvector.h:208:3: note: candidate: std::ptrdiff_t std::operator-(const std::_Bit_iterator_base&, const std::_Bit_iterator_base&)
operator-(const _Bit_iterator_base& __x, const _Bit_iterator_base& __y)
^
/usr/local/include/c++/5.3.0/bits/stl_bvector.h:208:3: note: no known conversion for argument 1 from 'std::_List_iterator<int>' to 'const std::_Bit_iterator_base&'
相关文章:
- 在 c++ 中的模板实例化中使用带有构造函数的类作为类型参数
- 如何解决一元"*"(有"字符")错误的无效类型参数?
- "std::shared_ptr":不是参数"_Ty"的有效模板类型参数
- 具有可变参数非类型参数的模板专用化
- 函数类型参数的模板参数推导
- PowerShell 使用结构类型参数调用 C++ DLL 的导出函数
- 对于非常量指针类型的参数,未调用具有常量指针模板类型参数的功能
- 为模板传递非类型参数 agument
- 为什么带有类型参数的运算符 () 可以应用于 result_of 上下文中的类型?
- 使用其他模板类型参数作为要在函数签名中使用的类型别名声明
- 如何避免具有相同类型参数的函数中的错误
- 将内置类型变量传递给只有一个类类型参数的"+"运算符函数时自动类型转换的构造函数
- c++非类型参数包扩展
- 如何实现对参数顺序不可知的std::same_as的广义形式(即对于两个以上的类型参数)
- 在不同的模板参数包之间分发非类型参数包
- 如何在使用容器和字符串时强制使用显式分配器类型参数
- 错误:一元"*"的类型参数无效(具有"int"):使用 mergesort 计算
- EXPECT_CALL具有 unique_ptr 引用类型参数的模拟函数
- 作为模板类型参数,为什么 type[N] 与其专用版本不匹配----模板<类 T>类 S<T[]>
- C++ 模板:重载时找不到基类类型参数方法