C++函数专用化

问题描述 投票:0回答:1

考虑以下片段。

class Stream {
    template <class T>
    void Write(const T& data);
};

class String { };

template <int N>
class Vector { };

template <>
void Stream::Write(const String& data) { }

到目前为止,一切都很好。现在,我想专门设计 Stream::Write 对于 Vectors与任何N。

template <int N>
void Stream::Write(const Vector<N>& data) { }

但是,这段代码无法编译。error C2244: 'Stream::Write': unable to match function definition to an existing declaration

你能解释一下我的代码有什么问题吗?是不是因为C++不允许部分函数特化?如果是的话,你能告诉我一个不需要修改的替代解决方案吗?Stream 类(因为它属于一个单独的库)。

c++ templates
1个回答
0
投票

如果你不能使用函数重载,因为Stream的接口是一成不变的,你有以下三种选择。

写一个单独的函数来实现写。

void write_impl(const String&) {
    // String implementation
}

template <int N>
void write_impl(const Vector<N>&) {
    // Default implementation
}

template <class T>
void Stream::Write(const T& data) {
    write_impl(data);
}

第二种选择,如果你想使用部分模板专用化 就是使用一个漏斗来实现。

template <class T>
struct write_impl_t;

template <>
struct write_impl_t<String> {
    void operator()(const String&) {
        // String implementation
    }
};


template <int N>
struct write_impl_t<Vector<N>> {
    void operator()(const Vector<N>&) {
        // Default implementation
    }
};


template <class T>
void Stream::Write(const T& data) {
    write_impl_t()(data);
}

最后一个选项是编译时的分支 if constexpr. 这只有在你能使用C++17及以上版本的情况下才能使用,而且你不能使用任何形式的类型推理,所以它不能解决你目前的问题,但可能会对你将来有所帮助。

template <class T>
void Stream::Write(const T& data) {
    if constexpr(std::is_same_v<T, String>) {
        // String implementation
    } else {
        // Default implementation
    }
}

1
投票

C++不允许函数模板特殊化,但是,它允许函数重载。你的代码中不是这个问题。根据这个错误,看起来你没有在Stream类中声明那个特殊的函数模板。你的代码应该是这样的。

class String { };

template <int N>
class Vector { };

class Stream {
    //function template
    template <class T>
    void Write(const T& data);

    //function overload for String class
    void Write(const String& data);

    //function template overload for Vector template
    template<int N>
    void Write(const Vector<N>& data);
};

如果你不能修改Stream类 原有的函数模板将接受所有Vector模板的类 在不修改相关类的情况下,你不能创建成员函数重载。

© www.soinside.com 2019 - 2024. All rights reserved.