[英]Why does this array allocation cause a segfault?
我試圖創建一個整數向量數組,但是在這段代碼中出現了段錯誤。
int main() {
vector<int> x[1000000];
}
我以為這是因為我超出了堆棧大小,所以我使用了動態分配,這似乎可以解決問題。 但是,為什么要這樣做:
vector<int> x[1000000];
int main() {
// do nothing
}
這項工作嗎?
int main() {
static vector<int> x[1000000];
}
這是因為在第一個示例中,數組是在堆棧上分配的,而您的實現對可用堆棧施加了太嚴格的限制。 您的第二個例子可能是靠運氣成功的。
請在程序存儲器的常規布局上參考此圖 ,訪問空白區域可能會導致分段錯誤(無論如何還是個壞主意)。
現在,當您分配非靜態局部變量時,直接數據將分配在堆棧上,但是構造函數也可以通過new
分配堆上的空間。 在您的情況下,構造函數也可能會分配內存( vector
的直接數據可能只有一個指針,但是您要分配一百萬個指針,因此至少8Mb的直接數據)。 可能是構造函數的存在,實際上會使您的程序出現段錯誤,因為在堆棧上分配的空間否則可能無法訪問(這是當您實際訪問超出堆棧限制的空間時,您會得到段錯誤)。
當您分配靜態或全局數據時,直接數據將分配在數據或BSS段中,如果預啟動數據(即,運行構造函數之前的數據,如果有的話)為零,它將被放置在BSS段中。 在您的情況下,數據很可能會放在BSS中。
現在需要注意的是與全球配置你到達主(而不是靜態的,不會運行,直到調用函數的第一次)之前的構造函數將運行,但你可能已經通過動態地分配new
的構造,並呼吁new
前main表示未定義的行為,您應該以為自己很幸運第二個示例沒有失敗(它可以這樣做而無需事先通知)。
從中學到的教訓是,最好僅在不需要復雜的構造函數的情況下才將大數據放入全局范圍。 如果您需要復雜的構造函數,則最好通過new
動態分配它。 當然,您可以將其作為本地static
對象放入,如果全局需要它,則返回對該對象的引用。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.