2015-10-19 53 views
0

我想讓這個簡單的程序工作,但我有一些錯誤,我不明白,因爲我是新的C++。我得到了一個沒有在我的函數初始化的範圍內聲明,並且無法在函數頭中使用數組。有人能幫助我嗎?在C++中使用數組

我的代碼如下:

#include <iostream> 
#include <string> 
using namespace std; 

char[][] initialize(char[][]); 

int main(){ 

    int array[3][3]; 
    initialize(array); 

    cout << array[0]; 

    return 0; 
} 

char[][] initialize(char[][] a){ 

    for(int i = 0; i < a.length(); i++){ 
     for(int j = 0; j < a[].length(); j++){ 
      a[i][j] = '\0'; 
     } 
    } 

    return a; 

} 
+2

原始數組沒有'length()'信息或函數。改用'std :: vector'(和'size()')。 –

+0

這不是我目前的主要問題。我得到一個沒有聲明的範圍內我的函數初始化和錯誤閱讀期望'['令牌之前的非限定id。關於爲什麼會出現這兩個錯誤以及如何解決它們的任何想法? – user3540561

+1

'char [] [] initialize(char [] []);'不是有效的聲明,因此它被拒絕。當然,當您嘗試調用該函數時,這也會導致「未聲明」錯誤。一個錯誤導致下一個錯誤。 –

回答

1

你可以簡單地通過初始化二維數組元素\0

char array[3][3] = {0}; 

現在,如果你想你的數組傳遞給函數(例如, print_2d_array()),並且爲了具有二維數組的維度,您需要按以下方式通過引用傳遞數組:

template<typename T, std::size_t N, std::size_t M> 
void print_2d_array(T (&a)[N][M]){ 

    for(int i = 0; i < N; ++i){ 
     for(int j = 0; j < M; ++j){ 
      std::cout << a[i][j] << " "; 
     } 
     std::cout << std::endl; 
    } 
} 

上面的函數打印任意類型/維數2d數組。

0

既然你知道數組引用的大小和傳球達陣,從而無需返回數組:

void initialize(char[][3]);//declaration 

功能:

void initialize(char a[][3]){ 
//no such function as array.lenth() 
for(int i = 0; i < 3; i++){ 
    for(int j = 0; j <3; j++){ 
     a[i][j] = '\0'; 
    } 
} 

此外,我可以看到你已經宣佈一個整數數組和傳遞給一個字符數組。所以要麼有一個整數數組或字符數組,但不是兩者都有。

1

如果您有固定大小的數組,您可以(也應該)使用std::array而不是原始C風格的數組。我會用你的initialize函數作爲例子,雖然有其他的方法來初始化數組。

#include <iostream> 
#include <string> 
#include <array> 
using namespace std; 

void initialize(std::array<std::array<char, 3>, 3>&); 

int main(){ 

    std::array<std::array<char, 3>, 3> array{}; 
    initialize(array); 

    return 0; 
} 

void initialize(std::array<std::array<char, 3>, 3>& a) { 
    for(auto& outer: a) { 
     for(auto& x: outer) { 
      x = '\0'; 
     } 
    } 
} 

當然,如果你想與字符串數組的工作,這就是我想你真的想,你應該這樣做並使用std::string,而不是零終止的C風格的字符串。

#include <iostream> 
#include <string> 
#include <array> 


int main(){ 

    std::array<std::string, 3> array{}; 
    array.fill(std::string(3, '\0')); 

    std::cout << array[0]; 

    return 0; 
} 

初始化是沒有必要在這種情況下,由於std::string正確地通過它的構造函數初始化。

如果您需要動態存儲,則應該使用std::vector而不是std::array。在任何情況下,我的建議是使用類型安全和方便的C++工具,而不是容易出錯,坦率地說 - 使用C等價物很痛苦。

+1

到目前爲止最好的回答。有兩件事:由於GCC中的一個bug,'array {};'需要'array {{}};'如果使用g ++和'array {}編譯;'使'initialize'函數變得冗餘。 – user4581301

0

訣竅之一:通過將函數定義放在main之前,可以省去前向聲明initialize的麻煩。這消除了一個潛在的錯誤來源。訣竅二:延斯打敗了我。使用std::array

招數三:使用std::vector

#include <iostream> 
#include <string> 
#include <vector> 
//using namespace std; this can be dangerous. Recommend the following as a replacement 
using std::vector; 
using std::cout; 

void initialize(vector<vector<char>> &a) // pass vector by reference 
{ 
    for(int i = 0; i < a.size(); i++) 
    { 
     for(int j = 0; j < a[i].size(); j++) 
     { 
      a[i][j] = '\0'; 
     } 
    } 
} 

int main() 
{ 
    vector<vector<char>> array(3, vector<char>(3)); 
    initialize(array); 

    cout << array[0][0]; 

    return 0; 
} 

兩點在這裏

  1. 使這有性能問題。向量(或數組陣列)的向量不太可能具有連續性(所有內存都在一個塊中),並且會導致將陣列數據從RAM加載到緩存中造成不必要的延遲。如果所有數據靠得很近,並且足夠小以適應,則一次緩存讀取將獲得整個數組。如果它是分散的,則每一塊需要單獨讀取,並且加載一塊可能會覆蓋另一塊,從而迫使它再次加載(這可能會在另一塊內存上寫入需要幾條指令的內存,迫使它重新讀取,並且這可能迫使另一片或另一個一塊來,循環往復。This is called Cache Thrashing

  2. 的std ::向量可以初始化數組內容對您

這裏需要文字因故保留格式下一個代碼塊。奇怪。

int main() 
{ 
    vector<vector<char>> array(3, vector<char>(3), '\0'); 
    cout << array[0][0]; 

    return 0; 
} 

如果由於分配限制,您不允許使用std::arraystd::vector,則容易編寫一個簡單的克隆std::array

struct TwoD 
{ 
    char array[3][3]; 
    char &operator()(int row, int col) 
    { 
     return array[row][col]; 
    } 
}; 

可能是你所需要的。