读书人

显式实例化跟显式具体化

发布时间: 2013-09-05 16:02:07 作者: rapoo

显式实例化和显式具体化
大家好~!!
我在看 C++ Primer Plus ,作者在介绍函数模板的显式实例化和显式具体化的时候,有下面这样的一句话:
显式实例化跟显式具体化

对句话不太理解,是不是不能像下面这样做?

template<typename T> //template
void foo(T t)
{
cout << t << endl;
return;
}

template void foo<double>(double); //Instantiation

template <> void foo<double>(double d) //Specialization
{
cout << "this is " << d << endl;
}

int main(int argv, char **argc)
{
foo(1.0);
return 0;
}

上面的g++和VS都报错了:
g++:error: specialization of 'void foo(T) [with T = double]' after instantiation
VS:error C2908: 显式专用化;已实例化“void foo<double>(double)”

按照g++的意思,难到instantiation放到specialization前面就可以了吗?

template<typename T> //template
void foo(T t)
{
cout << t << endl;
return;
}

template <> void foo<double>(double d) //Specialization
{
cout << "this is " << d << endl;
}

template void foo<double>(double); //Instantiation

int main(int argv, char **argc)
{
foo(1.0);
return 0;
}

结果,g++确实不报错了,也没有警告,而VS依然报错:
error C3416: “foo”: 显式专用化可能无法显式实例化

我想,那句话就是这个意思。而g++不报错,是不是因为模板函数在匹配类型的时候,具体化是优先于常规模板的,编译到Specialization的时候,找到匹配的了,然后就把Instantiation优化掉了??不作处理了??而且VS的错误信息有“可能”二字。。。

这只是我的胡乱猜想,请大家多多指教! 谢谢!!

显式实例化 显式具体化
[解决办法]
最好能把你的编译器版本和编译选项说清楚,因为新旧标准在这个问题上处理的不一样。
c++03 14.7/5 说:
No program shall explicitly instantiate any template more than once, both explicitly instantiate and explicitly specialize a template, or specialize a template more than once for a given set of template-arguments. An implementation is not required to diagnose a violation of this rule.


根据这个说法,主楼的两种写法都是错误的,目测你 VS 的编译器执行的是旧标准。

c++11 14.7/5 说:
For a given template and a given set of template-arguments,
— an explicit instantiation definition shall appear at most once in a program,
— an explicit specialization shall be defined at most once in a program (according to 3.2), and
— both an explicit instantiation and a declaration of an explicit specialization shall not appear in a program unless the explicit instantiation follows a declaration of the explicit specialization.
An implementation is not required to diagnose a violation of this rule.
根据这种定义,主楼第一种写法不满足第三条 unless 给出的条件,所以是错误;但是第二种写法则能够满足,所以编译无误,目测你的 g++ 编译器是按照新标准解释的。
另外,在 explicit specialization 和 explicit instantiation 同时存在的情况下,后者没有作用。
[解决办法]



还有一个疑问:这种也是“显式实例化”吗?它是在哪个位置生成了实例呢?


这个不叫显式实例化,叫显式模板实参,就是不需要编译器进行模板实参推演,由客户直接提供模板实参,提供显式模板实参会产生隐式实例化,同时也是隐式特例化。

读书人网 >C++

热点推荐