我得到“无效转换从`void *`到`std :: complex <double> *”</double>

时间:2013-12-31 13:26:16

标签: c++ calloc

我在下面有以下代码,

std::complex<double>** x;
x = calloc(10,sizeof(complex <double> *));

此代码无法使用以下错误消息进行编译。

error: invalid conversion from 'void*' to 'std::complex<double>*' [-fpermissive]

如何成功编译?为什么这段代码无法编译?

5 个答案:

答案 0 :(得分:6)

你正在尝试编写C ++,好像它是C一样,它允许像这样的危险的隐式转换。

要分配大小为10的动态数组,请使用

std::vector<std::complex<double>> numbers(10);

并且,如果你真的想要一个指向第一个元素的指针

x = numbers.data();

答案 1 :(得分:4)

在C ++中,void *不会自动转换为其他指针(与C不同)。因此,如果您在C ++中使用malloc和族,则需要自己投射结果。

但是,您应该注意malloc不了解C ++的构造函数。因此,如果您想要分配C ++对象(例如,不是C结构,或者更准确地说是POD),您应该使用new(以及相应的delete / delete[])关心构造函数和析构函数。

或者,您可以使用标准库提供的众多结构之一,例如std::vector

答案 2 :(得分:2)

问题。

此问题的代码,......

    x = calloc(10,sizeof(complex <double> *));

有两个原因:

  • 与C不同,C ++没有来自 void*的隐式转换

  • 通过C ++ new创建一个锯齿状数组已经足够糟糕了,使用C级分配函数进行处理通常是令人厌恶的(除非某些需要调用的函数需要)。 / p>

第一个要点是无法用C ++编译的原因。

<小时/>

该怎么做。

纯粹的技术修复是使用强制转换,然后最好使用C ++命名的强制转换,例如static_castreinterpret_cast。从void*转换,两者都可以很好地进行转换。但是,在我看来reinterpret_cast更正确地表达了概念操作,所以我选择 - if 我选择投射。

稍微好一点的解决方案是使用C ++ new而不是C calloc。对于new,您必须在末尾添加一个空括号,以获得calloc的保证零初始化。但主要的问题仍然是每个低水平和困难(很多工作)才能做到正确。

更好的通用解决方案是使用C ++容器类。

标准库提供std::vector,其中可以像这样构造锯齿状数组:

typedef complex<double> Complex;
typedef vector<Complex> ComplexVec;
typedef vector<ComplexVec> ComplexVec2D;

ComplexVec2D x( 10 );

然后每个ComplexVec都可以调整大小,因为std::vector是一个动态大小的数组。

<小时/>

如果你真的想要一个MATRIX怎么办。

如果你真的想要一个矩阵,即一个长度相等的数组数组,那么考虑一个C ++类而不是一个参差不齐的数组,它只能在单个向量中提供2D索引。

在C ++ 03风格中它可以像这样(关闭袖口代码):

typedef complex<double> Complex;

class ComplexMatric
{
private:
    vector<Complex> items_;
    int             width_;

public:
    Complex& operator()( int x, int y )
    { return items_[y*width_ + x]; }

    Complex const& operator()( int x, int y ) const
    { return items_[y*width_ + x]; }

    ComplexMatrix( int w, int h )
        : items_( w*h )
        , width_( w )
    {}
};

你会像这样使用它:

ComplexMatrix x( 10, some_height );

这包括正确分配和解除分配,甚至支持通过分配进行复制。

免责声明:编码器未触及代码。

答案 3 :(得分:1)

请尝试使用calloc运算符,而不是使用new[]。这是动态创建数组的C ++方法。

x = new complex<double>[10];

new[]返回一个指向运算符后面的任何类型的指针,在这种情况下,它是一个类型为complex<double>的指针,它指向一个complex<double>数组,里面有10个元素。 / p>

但请注意,您必须使用delete[]运算符来释放内存(而不是free())。否则,没有人知道会发生什么: - )。

delete[] x;

答案 4 :(得分:0)

假设您的x类型为std::complex<double>*,则会收到此错误,因为calloc会返回void指针。不允许-fpermissive隐式强制转换。因此,您必须在void*std::complex<double>*之间进行投射。但是,在C ++中,建议使用new代替malloccalloc,我个人建议您使用std::vector