c++ - c语言栈溢出




在C++程序中堆栈溢出错误 (2)

所以我有这个复杂的类,我想有一个复杂的二维数组这是代码的一部分,而不是所有的代码

class Complex {
public:
    /* construction/destruction */
    Complex(double r, double i)     { this->r = r; this->i = i; }
    Complex()                       { r=0.0; i=0.0; }
    ~Complex()                      { r=0.0; i=0.0; }
        /* operations */
    Complex operator+(Complex &c)   { return Complex( r+c.r, i+c.i ); }
        double r, i;
};

int main()
{
const int HEIGHT = 256;
const int WIDTH = 256;
Complex G[HEIGHT][WIDTH];
}

所以复线G [HEIGHT] [WIDTH]; 是导致问题的线,为什么?


任何想法为什么?

一些编译器默认栈大小为1MB。 您正在分配65536 Complex对象,每个对象占用2 * sizeof(double)内存。 假设double为8个字节(这个信息是实现定义的),你正在有效地试图分配16×65536字节(不考虑可能的填充),它是1048576字节,导致溢出。

另一种方法是使用动态分配的包装器,模拟一个二维数组索引,沿着这一行:

template<std::size_t A, std::size_t B>
class G {
private:
    std::unique_ptr<Complex[]> mem;
public:
    G() : mem(new Complex[A * B]) {}
    Complex& operator()(std::size_t a, std::size_t b) {
        return mem[a * B + b];
    }
    Complex  operator()(std::size_t a, std::size_t b) const {
        return mem[a * B + b];
    }
};

那么你的程序简单地变成:

int main(int, char*[]) {
    G<256, 256> g;
    g(0, 0) = ...;
}

当然你可以推广你的包装G为模板的泛型类型,但这超出了这个答案的范围。

在附注中,你是析构函数:

~Complex() { r=0.0; i=0.0; }

没用。 当它离开示波器时,不要重新初始化将被销毁的内存。


Visual Studio的默认堆栈大小为1MB,如下所示:

Complex G[HEIGHT][WIDTH];

将只有大约1MB,你可以使用/ F来修改这个文件( 我的重点 ):

没有这个选项,堆栈大小默认为1 MB 。 数字参数可以是十进制或C语言符号。 参数的范围可以从1到链接器接受的最大堆栈大小。 链接器将指定值四舍五入到最接近的4个字节。 / F和number之间的空格是可选的。

最明显的选择是通过newstd :: vector使用动态内存分配。

据我所知, Visual Studio实际上有一个较小的默认堆栈大小:

platform    default size       
=====================================
SunOS/Solaris  8192K bytes
Linux          8192K bytes
Windows        1024K bytes
cygwin         2048K bytes
Mac OS X       8192K bytes




pointers