Dependent names

编译下述代码时遇到了第一次遇到的问题

1
2
3
4
5
6
7
8
9
// 将boost::geometry中的box转换成自定义的Boundary
template <typename NumType = double>
Boundary<NumType, 2> fromBoost(
const boost::geometry::model::box<boost::geometry::model::point<NumType, 2,boost::geometry::cs::cartesian>>& box)
{
return Boundary<NumType, 2>(Vec<NumType,2>(box.min_corner().get<0>(), box.min_corner().get<1>()),
Vec<NumType, 2>(box.max_corner().get<0>(), box.max_corner().get<1>()));

}

这段代码在 VS2019 C++17 的标准下能编译过了,但是在 Apple Clang 下检查时,box.min_corner().get<0>() 等函数却报了一个第一次见的错误

1
missing 'template' keyword prior to dependent template name 'get'

查询了一下,发现是 C++ 模板里面的内容Dependent names,内容有不少,大致的概括下就是代码在语法解析时,有时候可以同时表示多种意思,这时候编译器需要手工添加的一些标识来确认需要的是什么意思(特别是在模板中)。例如下面模板代码中

1
T * t

如果T是一个类型名,那则声明了一个指针,如果T是一个变量则进行operator*(),所以T是并不是一个明确的声明,这时候就是一个 dependent name,依赖于上下文才能明确表明它是什么。
所以一开始的代码要改为

1
2
3
4
5
6
7
8
template <typename NumType = double>
Boundary<NumType, 2> fromBoost(
const boost::geometry::model::box<boost::geometry::model::point<NumType, 2,boost::geometry::cs::cartesian>>& box)
{
using point = boost::geometry::model::point<NumType, 2,boost::geometry::cs::cartesian>;
return Boundary<NumType, 2>(Vec<NumType,2>(box.min_corner().template get<0>(), box.min_corner().template get<1>()),
Vec<NumType, 2>(box.max_corner().template get<0>(), box.max_corner().template get<1>()));
}

还是第一次知道.的和->操作符后面是可以接template