[英]Unknown crash in a C++ Memory Pointers Exercise
我最近寫了一個程序來幫助我理解C ++中的內存指針的基礎,我選擇了一個簡單的質數查找器。
我終於得到它的工作。 (是的,用於調試!)
我讓它運行以查看進展情況,它達到素數#815389,我的冗長告訴我是65076素數,我遇到了應用程序崩潰。 我能想到的一件事是我的整數溢出,所以我將它們更改為多頭,它卡在同一位置。
有人能夠幫助解釋造成這種情況的限制嗎?
comp:WinVista 64位家庭高級版,6GB ram AMD 4800+ X2程序在4,664K內存使用時崩潰
資源:
#include <cstdlib>
#include <iostream>
\\\\(Backslashes added for readability)
using namespace std;
long number;
long numnum;
class num;
class num {
public:
long i;
void check();
bool nxt;
num* nxtnum;
};
void num::check() {
if (number % i != 0) {
if (nxt == true) {
(*nxtnum).check();
} else {
nxtnum = new num();
(*nxtnum).i = number;
numnum++;
cout << numnum << ":" << number << ", ";
nxt = true;
};
};
};
int main(long argc, char *argv[]){
numnum = 1;
cout << numnum << ":" << 2 << ", ";
num two;
two.i = 2;
for (number = 3; 1<=1000001; number++) {
two.check();
};
cout << endl;
system("PAUSE");
return EXIT_SUCCESS;
};
(不要管用戶名,它只是我使用的別名,所以我可以通過Google跟蹤我的所有帖子)
堆棧溢出? 我看到check
是遞歸的。
我猜出two.nxt沒有初始化的事實。 在C語言中,原始數據類型不會被初始化,這意味着它們具有現在正在占用的任何內存中發生的任何事情的值。 這意味着在main()中更可能是two.nxt = true,這將導致check()在無效指針上運行。 嘗試將其顯式設置為false,看看是否適合您。
[edit]如果這是問題所在,則更重要的初始化是在check()中分配新的num時。
肖恩是正確的,two.nxt從未初始化。 實際上,從未為num的任何實例初始化num.nxt。 如果使類更健壯,則成員nxt是不必要的。 可以使用nxt指針代替:
class num
{
private:
long i;
num *nxtnum;
public:
num (long value) : i (value), nxtnum (0) { }
void check ()
{
if (number % i != 0)
{
if (nxtnum)
{
nxtnum->check ();
}
else
{
nxtnum = new num (number);
cout << ++numnum << ":" << number << ", ";
}
}
};
當然,遞歸性質可能是主要的罪魁禍首,因為您可能正在運行調試版本,所以隱藏了初始化問題。 練習是將遞歸形式轉換為迭代形式。
我可以看到幾個問題:
正如肖恩·愛德華茲(Sean Edwards)所提到的那樣,num類沒有構造函數,因此新創建的num的成員中充滿了幾乎是隨機的垃圾。 而且該隨機垃圾可能包括將nxt設置為非零值。 我將添加以下構造函數以為其提供一組安全的默認值:
num :: num():i(0),nxt(false),nxtnum(0){}
您實際上並不需要布爾值,我只是檢查nxtnum是否為非零。
順便說一句,如果您使用的是Microsoft編譯器,則在定位x64時int和long的大小相同。 您的主要功能中也有一個無限循環,因為1總是<= 1000001。
我已經開始運作了,謝謝Skizz
#include <cstdlib>
#include <iostream>
#include <windows.h>
using namespace std;
long number;
long numnum;
class num;
num *two;
num *nn;
num *bre;
class num
{
private:
long i;
num *nxtnum;
public:
num (long value) : i (value), nxtnum (0) { }
void *check ()
{
if (number % i != 0)
{
if (nxtnum)
{
//nxtnum->check ();
nn = nxtnum;
}
else
{
nxtnum = new num(number);
cout << ++numnum << ":" << number << ", ";
nn = bre;
}
}else{nn=bre;}
}
};
int main(long argc, char *argv[])
{
numnum = 1;
cout << numnum << ":" << 2 << ", ";
two = new num(2);
nn=two;
for (number = 3; 1<=1000001; number++) {
while (nn!=bre){
nn->check();
Sleep(0);
}
nn=two;
};
cout << endl;
system("PAUSE");
return EXIT_SUCCESS;
};
對於那些有興趣的人
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.