2010-04-21 91 views
1

我正在寫一個函數,它需要一個字符串,字符串指針和一個int。 函數根據一組規則拆分字符串,並將每個標記放入一個數組中。我需要使用int變量中的元素數等方式將函數返回給函數。我被卡住了,因爲我無法使用auto,所以我不能使用auto,因爲它是銷燬的,我不願意使用new作爲我覺得這是不完整的。C++數組傳遞困境

我對如何解決這個問題有其他想法,但希望看到其他人如何去做這件事。我也可能是錯的,它可能會傳遞一個數組中的自動。我也可以不使用向量,所以有一個複製構造函數。

矢量無法使用,因爲這是我的一個挑戰,我被問及不能用於模板。

+0

爲什麼你認爲你不能使用的載體? – 2010-04-21 10:04:45

+0

出於好奇,爲什麼不能使用'vector'? – 2010-04-21 10:04:58

+0

因爲這是我選擇不使用矢量。 – Thomas 2010-04-21 10:06:36

回答

2

這是一個C而不是C++的問題,給出了這些限制。

返回數組的常用C模式實際上是讓調用者傳入一個數組來填充。這讓調用者決定分配(並因此取消分配)。

你的函數原型看起來像

int Function(string str1, string_ptr str2, int n, int* pOutArray, int cOutArray); 

當函數返回書面pOutArray元素的數量。

在執行過程中,您將pOutArray設置爲NULL,在這種情況下,您只需計算元素的數量,然後返回該值。這使您可以根據您的需要調用函數中的幾種方法之一: -

int out[5]={0}; 
int cFilled = Function(s1,s2,x,out,_countof(out)); 
// Further code can use up to 5<cFilled elements from the array. 

,或者

int cElt = Function(s1,s2,x,NULL,0); 
int* pOut = malloc(sizeof(int)*cElt); 
Function(s1,s2,x,pOut,cElt); 
// pOut now contains exactly the number of elements extracted. 
free(pOut); 
1

自然選擇當然是要通過結果爲std::vector<std::string>。如果你不想使用這種方法有兩種選擇:

  1. 讓代碼的客戶端提供結果的存儲,在這種情況下,它是一個好主意,客戶端通過的大小提供的存儲也是如此。
  2. new爲結果分配空間,我認爲這是一個更好,更穩健的選擇。您當然必須確保客戶端稍後使用delete的正確版本刪除內存或提供一種特殊機制來釋放內存。
0

如果要返回固定大小的數組,可以使用boost::array。但是,如果你不希望添加的升壓依賴,簡單的解決方案是創建一個數據結構與固定大小的數組,如:

 
template<typename T, std::size_t SIZE> 
struct array_wrapper 
{ 
    T array[SIZE]; 
}; 

如果大小會發生變化,然後用std::vector真確實最有意義。請記住,返回包裝類(如上所述)仍將導致創建副本(儘管由編譯器)。所以,你實際上沒有通過價值傳遞大的結果而不是通過在堆上構建它並傳遞指向分配的數據的指針來獲得任何節省,所以你的需求是沒有意義的。

0

通過'char & **'和'int & *'參數並在那裏分配令牌,將釋放內存的責任留給呼叫者。 現代標準不是很好,但工程。

0

如果您選擇不使用管理內存的標準方法(即std :: vector),那麼您將不得不做出選擇。

的三個基本選項:

  1. 來電管理內存。調用者傳入一塊內存(可能是一個int,指定該數組的大小)。你填充該數組。函數不需要做內存分配。
  2. 被調用者管理內存。該函數分配一個足夠大的塊,填充它,然後返回一個指向它的指針。
  3. 合作。調用者傳遞一個回調函數,被調用者使用該函數分配該塊。

選項(2)由於某人需要釋放內存這一事實而變得複雜。作爲API的一部分,您需要指定函數是否稍後清除阻塞(以及何時),或者調用者是否負責。

選項(3)可能是矯枉過正 - 你需要編寫一個函數來調用主函數。選項(1)因此是最好的(如果你不能使用矢量)。這是一個非常標準的模式 - 例如,低級別的Windows API使用該模式。

基本上,內存管理必須記錄爲API的一部分。