获取 ostream 的插入运算符

Getting ostream's Insertion Operators

我有一个 class,我想包装一个 ostringstream。我是这样处理的:

class Foo {
    ostringstream os;
public:
    template <typename T>
    decltype(ostream() << T(), Foo)& operator <<(const T& param) {
        os << param;
        return *this;
    }
}

我的意图是免费获得为 ostream 定义的任何运算符。但我收到编译错误:

error C2893: Failed to specialize function template unknown-type &Foo::operator <<(const T &)

我是不是用错了decltype

std::ostream没有默认构造函数,Foo也不是可以在decltype中使用的表达式。相反,您可以在第一个表达式中直接使用 os。为了 return Foo& 更容易,我会使用尾随 return 类型并使用 *this

template <typename T>
auto operator<<(const T& param) -> decltype(os << param, *this);

这纯粹是基于0x499602D2's answer and your link to the missing overloads 10-12

我不确定用什么函数来测试重载 11,但是 10 和 12 是用 std::hexstd::endl 测试的。

#include <iomanip>
#include <iostream>
#include <sstream>

class Foo {
private:
    std::ostringstream os{};

public:
    using char_type = std::ostringstream::char_type;
    using traits_type = std::ostringstream::traits_type;

    // generic, with perfect forwarding instead of "const T&"
    template<typename T>
    auto operator<<(T&& param) -> decltype(os << std::forward<T>(param), *this) {
        os << std::forward<T>(param);
        return *this;
    }

    // overload 10
    Foo& operator<<(std::ios_base& (*func)(std::ios_base&)) {
        func(os);
        return *this;
    }

    // overload 11
    Foo& operator<<(std::basic_ios<char_type, traits_type>& (*func)(
        std::basic_ios<char_type, traits_type>&)) {
        func(os);
        return *this;
    }

    // overload 12
    Foo& operator<<(std::basic_ostream<char_type, traits_type>& (*func)(
        std::basic_ostream<char_type, traits_type>&)) {
        func(os);
        return *this;
    }

    auto str() { return os.str(); }
};

int main() {
    Foo a;

    a << "Hello Worl";      // generic
    a << std::hex << 13;    // 10 + generic
    a << std::endl;         // 12

    std::cout << a.str() << "\n";
}