矩阵构造函数的括号括起来的初始值设定项在类型 std::complex<double> 中失败 >

Brace-enclosed initializer for matrix constructor fail in type std::complex<double> >

我为我的矩阵 class 实现了一个构造函数,以使用嵌套 std::initializer_list 进行大括号括起来的初始化。构造函数适用于主要类型:`int`、`double`;但会呈现“复杂”的错误阅读。如何解决这个错误阅读?

矩阵class

template <typename T> class xxx
{
 public:
     T *ptr;
     int col, row, size;
     xxx() = delete;
     xxx(const int i, const int j):row(i), col(j), size(i*j)
     {
         ptr = new T [this->size] ;
     }
     xxx(const std::initializer_list< std::initializer_list<T> > s):xxx(s.size(), s.begin()->size())
     {
       int j = 0;
       for (const auto& i : s) {  std::copy (i.begin(), i.end(), ptr + j*col); ++j ; }
    }
    ~xxx() {delete [] this->ptr;}
     T operator()(const int i, const int j) const { return ptr[i*col+j]; }
};

这里添加一个典型的输出重载以完成。

template <typename X> std::ostream& operator<<(std::ostream&p, const xxx<X>&a)
{
    for (int i=0; i<a.row; i++) {
        for (int j=0; j <a.col; j++) p << std::setw(6) << a(i, j);
        p << std::endl;
    }
    return p;
}

`double` 类型的第一个测试 main() 运行良好。

#include <iostream>
#include <initializer_list>
#include <iomanip>
#include <complex>
int main()
{
    xxx<double> x = {{1, 2,3,4} , {3, 4,5,6}, {5, 6,7,8} };
    std::cout << x << std::endl;
}

它打印出预期的内容:

$ ./a.exe
     1     2     3     4
     3     4     5     6
     5     6     7     8

然后,我尝试使用我感兴趣的另一种类型,`complex`:

int main()
{
    xxx< std::complex<double> > z = { {(1,2), (3,4)}, {(5,6), (7,8)} };
    std::cout << z << std::endl;
}

输出错误如下:

$ ./a.exe
 (2,0) (4,0)
 (6,0) (8,0)

想象部分缺失,真实部分取反想象部分的值。任何想法或建议将不胜感激。

您的问题与初始化列表无关。问题是这段代码

#include <iostream>
#include <complex>

int main()
{
    std::complex<double> x = (1,2);
    std::cout << x;
}

没有按照您的预期去做。输出是

(2,0)

因为 (1,2)comma operator 在工作。 std::complex<double> x = (1,2); 等同于 std::complex<double> x = 2;.

需要使用大括号进行初始化:

#include <iostream>
#include <complex>

int main()
{
    std::complex<double> x = {1,2};
    std::cout << x;
}

输出

(1,2)

PS 我强烈建议您使用 std::vector<T> 而不是 T* 来保存数据。由于不遵循 3/5 规则,目前复制 xxx 将导致未定义的行为。