1

我有以下std::begin围绕 Eigen3 矩阵的包装器:

namespace std {
template<class T, int nd> auto begin(Eigen::Matrix<T,nd,1>& v)
-> decltype(v.data()) { return v.data(); }
}

替换失败,我得到一个编译器错误(错误:没有匹配函数调用 'begin')。对于此重载,clang 输出以下内容:

.../file:line:char note: candidate template ignored: 
substitution failure [with T = double, nd = 4]
template<class T, int nd> auto begin(Eigen::Matrix<T,nd,1>& v)
                               ^

我希望选择此重载。我期望类型是doubleand int,即它们被推断为我希望它们被推断(并且希望是正确的)。通过查看该功能,我看不到任何可能实际失败的东西。

时不时我会遇到类似的错误。在这里,clang 告诉我:替换失败,我没有将这个函数放入重载决议集中。但是,这根本不能帮助我调试。为什么替换失败了?究竟什么地方不能代替?对我来说唯一明显的是编译器知道,但它故意不告诉我:(

  • 是否有可能强迫铿锵告诉我这里到底是什么失败了

  • 这个功能很简单,我遇到了问题。在更复杂的功能中,我猜事情只会变得更糟。你如何去调试这些类型的错误?

4

2 回答 2

2

您可以通过自己将替换为原始模板的剪切粘贴并查看编译器为完全专用代码发出的错误来调试替换失败。在这种情况下:

namespace std {
auto begin(Eigen::Matrix<double,4,1>& v)
-> decltype(v.data()) {
  typedef double T; // Not necessary in this example,
  const int nd = 4; // but define the parameters in general.
  return v.data();
}
}
于 2013-06-13T20:03:52.100 回答
1

好吧,这已被报告为clang中的错误。不幸的是,clang 开发人员仍然不知道修复它的最佳方法。在此之前,您可以使用 gcc 来报告回溯,或者您可以将此补丁应用到 clang 3.4。该补丁是一种快速破解,可以将替换失败变成错误。

于 2014-01-12T03:33:53.230 回答