更改复数输出格式

grz*_*zkv 6 c++ complex-numbers

complex<>C++标准库中有模板,它有一个重载的<<运算符,因此它以(real_part,im_part)格式输出复数.我需要更改该运算符对复数的行为,以便将输出格式更改为完全不同的输出格式.具体来说,我需要输出在表单中real_part\tim_part.我怎么做?

tem*_*def 7

没有直接的替代方法operator <<,但你确实有一些选择.首先,您可以编写自己的函数来打印复数:

template <typename T> void PrintComplex(const complex<T>& c) {
    /* ... */
}
Run Code Online (Sandbox Code Playgroud)

如果你仍想使用漂亮的流语法,那么你可以做的一个技巧就是创建一个包装类,complex然后定义自己的包装类,operator <<以不同的方式将其打印出来.例如:

template <typename T> class ComplexPrinter {
public:
    /* Conversion constructor allows for implicit conversions from
     * complex<T> to ComplexPrinter<T>.
     */
    ComplexPrinter(const complex<T>& value) : c(value) {
        // Handled in initializer list
    }

    /* Output the complex in your own format. */
    friend ostream& operator<< (ostream& out, const ComplexPrinter& cp) {
        /* ... print in your own format ... */
    }

private:
    complex<T> c;
};
Run Code Online (Sandbox Code Playgroud)

一旦你有这个,你可以写一些类似的东西

cout << ComplexPrinter<double>(myComplex) << endl;
Run Code Online (Sandbox Code Playgroud)

您可以通过编写类似这样的函数来为此包装对象,从而使其更加清晰:

template <typename T>
ComplexPrinter<T> wrap(const complex<T>& c) {
    return ComplexPrinter<T>(c);
}
Run Code Online (Sandbox Code Playgroud)

然后这让你写

cout << wrap(myComplex) << endl;
Run Code Online (Sandbox Code Playgroud)

哪个不完美,但非常好.

关于上面的包装器需要注意的一点是它有一个隐式转换构造函数,用于将complex<T>s 转换为ComplexPrinter<T>s.这意味着如果你有vector< complex<T> >,你可以通过调用使用自定义代码打印出来

vector< complex<double> > v = /* ... */
copy (v.begin(), v.end(), ostream_iterator< ComplexPrinter<double> >(cout, " "));
Run Code Online (Sandbox Code Playgroud)

在输出时,隐式转换构造函数会将您的complex<double>s转换为包装器,您的自定义代码将为您执行打印.

如果你想要非常冒险并且谨慎行事,你甚至可以编写课程,以便它只存储对原文的引用complex,如下所示:

template <typename T> class ComplexPrinter {
public:
    /* Conversion constructor allows for implicit conversions from
     * complex<T> to ComplexPrinter<T>.
     */
    ComplexPrinter(const complex<T>& value) : c(value) {
        // Handled in initializer list
    }

    /* Output the complex in your own format. */
    friend ostream& operator<< (ostream& out, const ComplexPrinter& cp) {
        /* ... print in your own format ... */
    }

private:
    const complex<T>& c;
};
Run Code Online (Sandbox Code Playgroud)

这完全消除了任何复制,只是使包装器成为真实的薄单板complex.(没有双关语).如果你这样做,你必须非常小心,不要在原始对象超出范围的范围边界传递这些对象,但如果它是你想要的,它可能会很好.

希望这可以帮助!