首先说下遇到的情况:

    这里在vc++6.0上建立了一个自定义模板类,再去覆盖这个类,分别使用部分覆盖,整体覆盖

    但在vs2015上去整体覆盖类会报错。

    错误如下:

错误原因:个人感觉是新版本的vs更接近与标准c++,有更好的解释欢迎留言,谢谢

解决方法:

    网上有类似的问题出现,C++标准文件(ISO/IEC 14882:2003)中这句很重要

    

所以自己的代码就差在覆盖类前加template<>

感兴趣的可以看下面的转载说明:https://blog.csdn.net/wdsm/article/details/7506712   写的挺好的,这里也有转载及附带声明

////////////////////////////////////////////////////////////////////////////////////////////////////////

最近在拜读侯捷老师的《STL源码剖析》,本着勤于实践的指导思想,使用gcc和vc分别编译运行了第27页的程序,此程序是用来测试SGI STL中的__STL_STATIC_TEMPLATE_MEMBER_BUG宏的。其代码如下:

#include<iostream>

using namespace std;

template<class T>

class testclass

{

public:

    static int _data;

};

int testclass<int>::_data = 1;

int testclass<char>::_data = 2;

int main()

{

    cout << testclass<int>::_data << endl;

    cout << testclass<char>::_data << endl;

    testclass<int> obji1, obji2;

    testclass<char> objc1, objc2;

    cout << obji1._data << endl;

    cout << obji2._data << endl;

    cout << objc1._data << endl;

    cout << objc2._data << endl;

    obji1._data = 3;

    objc2._data = 4;

    cout << obji1._data << endl;

    cout << obji2._data << endl;

    cout << objc1._data << endl;

    cout << objc2._data << endl;

    return 0;

}

    起初我使用的GCC是2.95.3-5(cygwin special)版本,一切如我所预料,编译运行顺利通过。然而,一时头脑发热,我想在较新版本上试试程序效果,使用MINGW32 gcc 4.5.4版本编译器——通过GNU官方资料来看,本版对C++ 03版本中规定的语言特性几乎全部支持。结果,在编译的时候,出现了如下错误提示:

D:\mingw32\bin>gcc c:\cygwin\home\config3.cpp -o c:\test.exe

c:\cygwin\home\config3.cpp:11:5: error: specializing member 'testclass<int>::_data' requires 'template<>' syntax

c:\cygwin\home\config3.cpp:12:5: error: specializing member 'testclass<char>::_data' requires 'template<>' syntax

    这是为什么呢?我又将代码放到VS2008和VC6环境下测试,顺利编译通过。看过上面的错误提示信息之后倒是提醒我,testclass<int>类似的写法表明我们针对testclass模板类进行了一次模板参数特化(explicit specialization)操作,按照c++教科书上面所说,模板特化操作语句前面需要加“template<>”修饰符。为了弄清楚真相,搬出C++标准文件(ISO/IEC 14882:2003)来,第14.7.3章节中明确的描述了模板特化语法为“template<>”形式前缀,以此告诉编译器这是一个模板特化行为。但是事情似乎总是存在例外,静态变量初始化操作中“template<>”形式语法在如下所述的情况中是不能够出现的,引用标准中原文如下:

A member of an explicitly specialized class is not implicitly instantiated from the member declaration of

the class template; instead, the member of the class template specialization shall itself be explicitly defined.

In this case, the definition of the class template explicit specialization shall be in scope at the point of decla-ration of the explicit specialization of the member.  The definition of an explicitly specialized class is unre-lated to the definition of a generated
specialization.  That is, its members need not have the same names,

types, etc. as the members of the a generated specialization.  Definitions of members of an explicitly spe-cialized class are defined in the same manner as members of normal classes, and not using the explicit specialization syntax.  [Example:

template<class T> struct A {

    void f(T) { /* ... */ }

};

template<> struct A<int> {

    void f(int);

};

void h()

{

    A<int> a;

    a.f(16); // A<int>::f must be defined somewhere

}

//explicit specialization syntax not used for a member of

//explicitly specialized class template specialization

void A<int>::f() { /* ... */ }

—end example]

简洁点讲,上文是说在定义特化类中的成员函数或是静态成员变量初始化等操作的时候,不需要“template<>”前缀。为了检验此特性,将先前的代码稍作修改:

#include<iostream>

using namespace std;

template<class T>

class testclass

{

public:

    static int _data;

};

template<>

class testclass<int>

{

public:

    static int _data;

};

int testclass<int>::_data = 1;

template<> int testclass<char>::_data = 2;

int main()

{

    cout << testclass<int>::_data << endl;

    cout << testclass<char>::_data << endl;

    testclass<int> obji1, obji2;

    testclass<char> objc1, objc2;

    cout << obji1._data << endl;

    cout << obji2._data << endl;

    cout << objc1._data << endl;

    cout << objc2._data << endl;

    obji1._data = 3;

    objc2._data = 4;

    cout << obji1._data << endl;

    cout << obji2._data << endl;

    cout << objc1._data << endl;

    cout << objc2._data << endl;

    return 0;

}

    以上程序在gcc 2.95.3版本、gcc 4.5.4版本、VS2008和VC6下面编译测试通过。

    综上所述,MS系列的编译器对C++标准的支持程度应该还是逊色于gcc(作者个人观点)。

///////////////////////////////////////////////////////////////////////////

//////////////转载文章//////////////////https://blog.csdn.net/wdsm/article/details/7506712

C++(VS2015)模板显式特化之template语法深入理解的更多相关文章

  1. C++模板显式实例化,隐式实例化,特化(具体化,偏特化)辨析

    最近再次看C++ PRIMER PLUS的时候看到这个部分感觉讲得很烂,前后口径不一致,所以写个辨析让自己明白的同时也希望对此不太清楚的朋友能搞懂. 总结一下,C++只有模板显式实例化(explici ...

  2. C++学习笔记36 (模板的细节明确template specialization)和显式实例(template instantiation)

    C++有时模板很可能无法处理某些类型的. 例如: #include <iostream> using namespace std; class man{ private: string n ...

  3. item 6: 当auto推导出一个不想要的类型时,使用显式类型初始化的语法

    本文翻译自<effective modern C++>,由于水平有限,故无法保证翻译完全正确,欢迎指出错误.谢谢! 博客已经迁移到这里啦 Item 5解释了比起显式指定类型,使用auto来 ...

  4. C++语言基础(19)-模板的显式具体化

    应用背景: 例如有下面的函数模板,它用来获取两个变量中较大的一个: template<class T> const T& Max(const T& a, const T&a ...

  5. C++的模板特化 和 STL中iterator_traits模板的偏特化

    C++中有类模板和函数模板,它们的定义如下所示: 类模板: template<class T1,class T2> class C { //... }; 函数模板: template< ...

  6. C++ - 模板类模板成员函数(member function template)隐式处理(implicit)变化

    模板类模板成员函数(member function template)隐式处理(implicit)变化 本文地址: http://blog.csdn.net/caroline_wendy/articl ...

  7. C++模板元编程(C++ template metaprogramming)

    实验平台:Win7,VS2013 Community,GCC 4.8.3(在线版) 所谓元编程就是编写直接生成或操纵程序的程序,C++ 模板给 C++ 语言提供了元编程的能力,模板使 C++ 编程变得 ...

  8. Effective Modern C++翻译(7)-条款6:当auto推导出意外的类型时,使用显式的类型初始化语义

    条款6:当auto推导出意外的类型时,使用显式的类型初始化语义 条款5解释了使用auto来声明变量比使用精确的类型声明多了了很多的技术优势,但有的时候,当你想要zag的时候,auto可能会推导出了zi ...

  9. [Effective Modern C++] Item 6. Use the explicitly typed initializer idiom when auto deduces undesired types - 当推断意外类型时使用显式的类型初始化语句

    条款6 当推断意外类型时使用显式的类型初始化语句 基础知识 当使用std::vector<bool>的时候,类型推断会出现问题: std::vector<bool> featu ...

随机推荐

  1. Android开发之数据存储——SharedPreferences基础知识详解,饿补学会基本知识,开发者必会它的用法。

    一.数据存储选项:Data Storage --Storage Options[重点] 1.Shared Preferences Store private primitive data in key ...

  2. 使用easyexcel时遇到Could not initialize class net.sf.cglib.beans.BeanMap$Generator

    可以访问 这里 查看更多关于大数据平台建设的原创文章. 上一篇文章 Maven项目为什么会产生NoClassDefFoundError的jar包冲突 结合了大量的图解,详细介绍了Maven项目产生ja ...

  3. 小程序开发-页面导航栏navigation-bar组件

    导航栏navigation-bar 页面导航条配置节点,用于指定导航栏的一些属性.只能是 page-meta 组件内的第一个节点,需要配合它一同使用. 通过这个节点可以获得类似于调用 wx.setNa ...

  4. 一文搞懂WordPress建站

    文章首发于:https://zouwang.vip/ 日日夜夜的等待,WordPress建站教程终于来了.本篇文章适用于第一次建站的小白,帮助你从零搭建起一个属于自己的网站,既然是从零,那么我就会带着 ...

  5. leetcode刷题-36有效的数独

    题目 判断一个 9x9 的数独是否有效.只需要根据以下规则,验证已经填入的数字是否有效即可. 数字 1-9 在每一行只能出现一次.数字 1-9 在每一列只能出现一次.数字 1-9 在每一个以粗实线分隔 ...

  6. 虚拟机安装centos常见问题

    一.centos下载安装 环境:win10系统,虚拟机vm12, centos6.5 http://vault.centos.org/ 链接打开 选择6.5=>isos/=>x86_64= ...

  7. 关于Nginx mmap(MAP_ANON|MAP_SHARED, 314572800)报错

    mmap 报错解决 今天修改了一下测试环境的Nginx的nginx.conf,然后做检测的时候报了一个错误 /usr/local/bin/nginx -c /usr/local/etc/openres ...

  8. shell进行微信报警的简单应用

    一.企业微信注册地址: https://work.weixin.qq.com/?from=openApi二.请求格式 1.获取token的方法 curl -s 'https://qyapi.weixi ...

  9. Centos7,PHP7安装swoole

    Swoole详细介绍及如何使用,这里暂时不做说明,可以参考一下文档:https://wiki.swoole.com/ 源码编译安装 下载地址如下: https://github.com/swoole/ ...

  10. js中的选择排序和冒泡排序

    var arr = [12,25,8,16,14]; console.log("排序前数组,",arr) //选择排序:第一轮,找出数组中最小的数,将第一项和最小的数互换位置.第二 ...