模板类偏特化语法

shr*_*ike 3 c++ templates

以下部分模板类专业化的基本示例,取自此 wiki 页面

template <typename Key, typename Value>
class KeyValuePair { /* something generic */ };

template <typename Key>
class KeyValuePair<Key, bool> { /* something specific to Value=bool */ };

KeyValuePair<int> kvpi;
Run Code Online (Sandbox Code Playgroud)

生成编译器错误:

prog.cpp:10:17: error: wrong number of template arguments (1, should be 2)  KeyValuePair<int> kvpi;
Run Code Online (Sandbox Code Playgroud)

为什么 ?我究竟做错了什么 ?应如何声明和实例化部分模板类特化?

我期望变量kvpi是 type 的部分专用模板类实例KeyValuePair<int,bool>

Who*_*aig 6

您似乎将部分专业化与默认模板参数混淆了。看来您还需要两者(原因未说明,但并不重要)。虽然不完全直观,但可以按如下方式完成:

#include <iostream>

template <typename Key, typename Value = bool>
class KeyValuePair
{
public:
    KeyValuePair()
    {
        std::cout << __PRETTY_FUNCTION__ << ':' << "original\n";
    }
};

template <typename Key>
class KeyValuePair<Key, bool>
{
public:
    KeyValuePair()
    {
        std::cout << __PRETTY_FUNCTION__ << ':' << "specialized\n";
    }
};


int main()
{
    KeyValuePair<int,int> kvp1;
    KeyValuePair<int> kvp2;
}
Run Code Online (Sandbox Code Playgroud)

输出

KeyValuePair<int, int>::KeyValuePair() [Key = int, Value = int]:original
KeyValuePair<int, bool>::KeyValuePair() [Key = int, Value = bool]:specialized
Run Code Online (Sandbox Code Playgroud)

一些令人困惑的部分是默认参数规范,但随后的模板将永远不会实际看到默认参数的成果,因为后来的专业化。在这种情况下,我更喜欢使用其默认参数列表向前声明模板。至少对我来说,它使阅读更容易一些。如果您觉得它提供了清晰性,您可以(或不)选择这样做。就像是:

template <typename Key, typename Value = bool>
class KeyValuePair;

template <typename Key, typename Value>
class KeyValuePair
{
public:
    KeyValuePair()
    {
        std::cout << __PRETTY_FUNCTION__ << ':' << "original\n";
    }
};

template <typename Key>
class KeyValuePair<Key, bool>
{
public:
    KeyValuePair()
    {
        std::cout << __PRETTY_FUNCTION__ << ':' << "specialized\n";
    }
};
Run Code Online (Sandbox Code Playgroud)


Gar*_*365 5

部分模板专业化不允许您忘记模板参数。你必须写:

KeyValuePair<int, bool> kvpib;
Run Code Online (Sandbox Code Playgroud)

并将使用正确的专业化。

但你可以使用继承来实现你想要的:

template <typename Key>
class KeyBoolPair : public KeyValuePair<Key, bool> {};

KeyBoolPair<int> kbpi;
Run Code Online (Sandbox Code Playgroud)

或者如果您使用 C++11 或更高版本:

template <typename Key>
using KeyBoolPairBis = KeyValuePair<Key, bool>;

KeyBoolPairBis<int> kbpbi;
Run Code Online (Sandbox Code Playgroud)

示例:http://coliru.stacked-crooked.com/a/5095fc5c358d291a