2017-04-23 112 views
1

我需要讀取.txt文件並將第一個數字用作函數getData中的數組大小。傳遞結構的動態數組C++

在我的代碼中,我能夠讀取文件並將其指定爲數組大小爲listSize。我也可以用.txt信息填充陣列的其餘部分。當我打印出getData函數中的數組時,它可以工作。

問題是,當我嘗試訪問getData函數之外的數組時,我的程序崩潰了。我對指針和一般的C++都很陌生。我認爲我沒有通過它或正確地調用它。我很難找到信息來幫助我解決問題。

如何訪問我在getData中創建的陣列?

#include <iostream> 
#include <fstream> 
#include <iomanip> 
#include <string> 

using namespace std; 

struct menuItemType 
{ 
    string menuItem; 
    double menuPrice; 
}; 

void getData(int& listSize, menuItemType menuList[], int orderList[]); 

int main() 
{ 

    menuItemType *menuList = 0; //-----pointers 
    int   *orderList = 0; 
    int   listSize; 

    getData(listSize, menuList, orderList); 

    cout << menuList[0].menuItem; //-----This is what crashes the program 

    return 0; 
} 

//-----Get Menu Function 
void getData(int& listSize, menuItemType menuList[], int orderList[]) 
{ 
    //-----Declare inFile 
    ifstream inFile; 
    string price, size; 

    //-----Open inFile 
    inFile.open("Ch9_Ex5Data.txt"); 

    //-----Get Amount of Items, Convert to int 
    getline(inFile, size); 
    listSize = stoi(size); 

    //-----Set Array Size 
    menuList = new menuItemType[listSize]; 
    orderList = new int[listSize]; 

    //-----Get Menu 
    for (int x = 0; x < listSize; x++) 
    { 
     //-----Get menuItem 
     getline(inFile, menuList[x].menuItem); 

     //-----Get menuPrice convert to double 
     getline(inFile, price); 
     menuList[x].menuPrice = stod(price); 
    } 

    //------PRINT WORKS HERE ----- This print made me think i created the 
    //arrays correctly 
    for (int x = 0; x < listSize; x++) 
    { 
     cout << menuList[x].menuItem << endl 
      << menuList[x].menuPrice 
      << endl; 
    } 

    inFile.close(); 
} 

getData設置menuListorderList的的.txt

8 
Plain Egg 
1.45 
Bacon and Egg 
2.45 
Muffin 
0.99 
French Toast 
1.99 
Fruit Basket 
2.49 
Cereal 
0.69 
Coffee 
0.50 
Tea 
0.75 
+0

傳遞指向數組中第一個元素的指針以及一個表示數組大小的整數。 '通過(StructArray * sa,int sizeArray)' –

回答

1

內容不main更新指針。請將您使用的指針引用:

void getData(int& listSize, menuItemType*& menuList, int*& orderList); 

更妙的是,使用引用std::vector並退出與所擁有的指針和newdelete周圍搞混。

+0

謝謝!我一直被卡住的時間比id還要承認。 –

1

讓我們用一個更好的C++重寫你的代碼,並加以解釋。 :)

#include <iostream> 
#include <fstream> 
#include <iomanip> 
#include <string> 

不要做使用空間std,只是因爲你可以輸入更少的東西,命名空間,告訴你,你調用這個特別的事情是從哪裏來的幫助你。如果你真的想寫入字符串,而不是的std :: string,拉那特別的事情,而不是整個命名空間,就像這樣:

using std::string; 

你的結構似乎是正確的,但你需要選擇,如果你的類型將與首都啓動還是不行,我總是開始我的類型的資本,但是這是一個選擇:

struct MenuItemType 
{ 
    string menuItem; 
    double menuPrice; 
}; 

現在,你應該的getData,好,讓您的數據。所以類型很重要。你的數據不是'你'聲明的'void',它是一個MenuItemType數組,你可以將它們聲明爲vector,甚至不關心指針。

其他的事情:getData中的所有參數都不應該是參數 - 它們都是你從程序解析的文本文件中得到的所有東西,所以對於getData唯一重要的是文本文件,所以這是你的變數。

std::vector<MenuItemType> getData(const std::string& textFile) 
{ 
    std::ifstream inFile; 
    std::string price, size, item; 
    inFile.open(textFile); 
    getline(inFile, size); 
    int listSize = stoi(size); 

    std::vector<MenuItemType> result; 
    result.reserve(listSize); 

    for (int x = 0; x < listSize; x++) 
    { 
     getline(inFile, item); 
     getline(inFile, price); 
     result.push_back(MenuItemType{item, stod(price)}); 
    } 
    return result; 
} 

看看我沒有關閉文件?它將在您離開該功能後立即關閉,除非在功能結束前需要關閉該文件,否則無需調用該功能。

豎起大拇指規則:除非必須處理指針。

至於你的主要功能:

int main() 
{ 
    std::vector<MenuItemType> menuList = getData("Ch9_Ex5Data.txt"); 
    cout << menuList[0].menuItem; 
    return 0; 
} 

你可以重寫以更快的方式,如果你確信你使用的是什麼類型的,上面的代碼就相當於這一個:

int main() 
{ 
    auto menuList = getData("Ch9_Ex5Data.txt"); 
    cout << menuList[0].menuItem; 
    return 0; 
} 
+0

優秀信息!謝謝,我目前是一名學生,我們正在討論結構,指針,函數等等。我們還沒有得到載體。你在我的代碼中看到的是關於我的知識程度。像你這樣的評論可以幫助我進步,謝謝! –

+0

不客氣。一件事,目前教現代C++的方法是留下一些高級主題,比如稍後指出,當學生更好地接受語言時。 –