2016-11-26 84 views
1

請看看下面的代碼:什麼時候分配和初始化變量?

template <typename T> 
class matrix 
{ 
    private: 
     std::vector<T> vec_; 

public: 
    matrix(size_t rows , size_t cols) : rows_(rows) , cols_(cols) , vec_(rows_ * cols_) 
    { 
    }  
    size_t rows_; 
    size_t cols_; 

}; 

這是聲明一個類的方法。我只是想知道std::vector被分配的位置以及它正在初始化的位置?

當我聲明變量時會發生什麼?在構造函數被調用或在構造函數中分配並初始化之前,它是否在堆棧中分配空間?

是什麼聲明矢量大小爲10

std::vector<T> vec_(10); 

,並呼籲vec_的構造與構造尺寸10之間的區別?

matrix() : vec_(10) 

我想了解如何在C++中分配和初始化對象。

我也無需調用的std::vector

matrix() {} 

這到底是怎麼發生的構造函數創建一個構造?因爲我不是調用vector的構造函數,編譯器會調用它自己的嗎?可以使用矢量對象嗎?還是自動調用,因爲我宣稱std::vector是我班的變量?

還初始化爲std::vector vec(10),與調用resize/reserve具有相同的效果。哪一個更接近?

+1

「這是一種聲明類的方法」 - 不。這是**模板**的定義;該模板是用於定義類的模式。 –

回答

2

代碼:

private: 
    std::vector<T> vec_(10); 

不編譯爲薄熙來說。但是你可以在C這樣做是合法的&性能方法++ 11(如高性能因爲copy elision:賦值操作符很可能變成一個拷貝構造函數,因爲對象在這個非常行初始化):

private: 
    std::vector<T> vec = std::vector<T>(10); 

所以,以前的結構,這一個:因爲你不vec_將建一次,裏面坐了10個元素,酷似resize會做,但它的速度更快:

public: 
    matrix() : vec_(10) 

做同樣的必須創建一個空向量調整它。

對於問題的第二部分:如果使用默認構造函數創建實例,編譯器將調用所有類成員的默認構造函數,因此它非常安全。

請注意:POD對象沒有歸零,這可能是一個問題,所以最好將指針設置爲nullptr,將整數設置爲0等等,或者您獲得未初始化的值,當進入具有無效的析構函數時不好指針傳遞到delete ...

當然,它將無法編譯,如果成員擁有唯一的非默認的構造函數(需要一個參數)。

+0

如果我在vec_上調用push_back將會是第11個項目,那麼對嗎? – nnrales

+1

絕對。這就像'resize',而不是'reserve' –

+0

因此,如果我編寫一個構造函數,它只爲某些成員調用構造函數,而不是其他函數,編譯器會自動調用cstor來處理那些我沒有調用的構造函數? – nnrales

2

類對象的成員按照聲明的順序進行初始化。在這種情況下,它是這樣的順序:

private: 
    std::vector<T> vec_; 

public: 
    size_t rows_; 
    size_t cols_; 

所以執行初始化列表時

matrix(size_t rows , size_t cols) : rows_(rows) , cols_(cols) , vec_(rows_ * cols_) 

真正順序

vec_(rows_ * cols_), rows_(rows) , cols_(cols) 

他們之前被使用rows_cols_初始化。壞事會發生。

+0

我不知道。謝謝 ! – nnrales

+1

並沒有真正回答這個問題,但非常好的評論。請注意,g ++會提醒你。 –

+0

@jean - 當我寫回答時,問題被擴展了。我會嘗試添加更多信息。 –