2014-10-27 35 views
2

所以我已經超載運算符()爲2d數組類。對於我正在做的隨機測試,返回設置爲array[0][index]。現在只傳遞列設置爲0的索引(行)。如果索引小於行(那麼我們在下一行),它仍然返回數據,就像我指定了列一樣?C++二維數組索引與1參數(爲什麼這個工作?)

基本代碼示例:

class myArr 
{ 
private: 
    float array[3][3]; 
public: 
    myArr::myArr(float a1, float a2, ...) { array[0][0] = a1; array[0][1] = a2; ... } 
    //^the "..." just means, the same action till float a9/array[2][2] = a9; 
    float& operator() (unsigned index) { return array[0][index]; } 
    const float operator() (unsigned index) const { return array[0][index]; } 
}; 

int main() 
{ 
    myArr test(1, 2, 3, 4, 5, 6, 7, 8, 9); 
    std::cout << myArr(4) << std::endl; // Displays 5 
    myArr(4) = 0; // Set's element 4 to hold value 0 
    return 0; 
} 

奇怪的是這個作品。我可以用1個參數設置/獲取第5個元素。現在我想知道爲什麼/如何確切地起作用,當然它應該錯誤地出現「越界」或什麼。最後這是「安全」還是強烈建議不要這樣做?

我很少使用2D陣列,這主要是由於它們缺乏性能增益。

回答

6

數組連續存儲在內存中。在C++中,多維數組在內存中逐行存儲,所以我相信這是一個非常有效的內存,可以超越當前行進入下一行。如果您超出了二維陣列的最後一行,則會出現超出範圍的情況。

是否這是一件好事情是一個不同的問題。很明顯,用這種方式編寫代碼會導致讀者撓腦袋,試圖弄清楚你在做什麼,所以你想避免用這種方式編寫真正的代碼。

如果你聲明一個二維數組,那麼你會希望在數組的整個生命週期中保持這些語義,所以我強烈建議不要這樣做。

+0

啊,這是有道理的。嗯,我會避免這一點,謝謝你。 – SharkBytes 2014-10-27 19:59:24

+1

@ user3046336在極端優化的情況下,執行1D訪問可能會更快,而不是2D。除了這種情況,你的結論是避免它。 – 2014-10-27 20:03:44

+0

這是值得商榷的,它是否會導致未定義的行爲通過像這樣的數組末尾訪問(雖然我現在找不到相關的線程) – 2014-10-27 20:23:05

0

當您分配2d數組時,其內存是連續的。所以如果你分配一個3 * 3的浮點數組,你將分配9 * 4個連續的字節。 結果是:

&array[0][i] = array + 0*3 + i = array + i = array[i] 

所以「偶然」,你會得到正確的結果。

+0

更具體地說,您分配九個數組元素,每個元素佔用四個字節例如,假設sizeof(float)== 4。 – jia103 2014-10-27 19:53:12

相關問題