[英]How can I read .txt files, to inherited objects in c++?
我正在做一項作業,我必須在c ++中為體育組織創建一個數據庫,而無需使用STL(我創建了自己的列表和String)。 數據庫將數據保存在一個雙鏈表中,其中除了節點之外,還有數據,即團隊。 當然,不僅有一種類型的團隊,目前有三類。 這些對象,繼承了team對象。 除了讀取文本文件並由此創建對象之外,我已經使所有工作都可以進行。
我已經嘗試過創建一個標記,這是程序將要讀取的第一條信息,它將決定需要創建三個類中的哪一個,然后讀取其他數據,以創建新對象,然后將其放入在雙向鏈接列表的末尾。 不幸的是,它不起作用,而是什么也不做,繼續整個程序,就像什么也沒發生一樣。
void hozzaad(ListaElem *s, team *data) { ///adding to the end
ListaElem *iter = s;
while (iter->kov=NULL)
{
iter = iter->kov;
}
ListaElem *uj = new ListaElem(data);
uj->elozo = iter;
iter->kov = uj;
}
void listaz(ListaElem *s) { //print out all that is in the list
if (s == NULL) {
std::cout << "Ures lista" << std::endl;
return;
}
ListaElem *iter = s;
while (iter!=NULL)
{
iter->adat->kiirt(std::cout);
iter = iter->kov;
}
}
void listament(ListaElem *s, const char *a) { //this one creates the file
std::ofstream file;
file.open(a);
ListaElem *iter = s;
if (file.is_open()) {
while (iter != NULL) {
file << iter->adat->Getclub()<< "\n";
file << iter->adat->Getname() << "\n" << iter->adat->Getmember()<< "\n";
if (iter->adat->Getclub() == 1) {
file << iter->adat->Getsupport() << "\n";
}
if (iter->adat->Getclub() == 2) {
file << iter->adat->Getpompom() << "\n";
}
if (iter->adat->Getclub() == 3) {
file << iter->adat->Getname1() << "\n" << iter->adat->Getname2() << "\n";
}
iter = iter->kov;
}
}
else
{
std::cout << "Nem tudom kinyitni a file-t";
}
file.close();
return;
};
void test4() { // the basic test
Handball c("Kezes HC", 21, 50000);
team adat("", 0);
ListaElem *egyik = new ListaElem(&adat);
hozzaad(egyik,&c);
ListaElem *uj = new ListaElem(&adat);
listament(egyik, "test.txt");
std::ifstream file;
file.open("test.txt");
if (!(file.is_open())) {
std::cout << "hiba\n";
return;
}
int micsoda;
while (file >> micsoda);
{
if (micsoda == 1) {
String beolvas("");
int m;
int d;
getline(file, beolvas);
file >> m;
file >> d;
Handball ujh(beolvas, m, d);
hozzaad(uj, &ujh);
beolvas = "";
}
if (micsoda == 2) {
String fbeolvas("");
int fm;
String e1("");
String e2("");
getline(file, fbeolvas);
file >> fm;
getline(file, e1);
getline(file, e2);
football ujh(fbeolvas, fm, e1, e2);
hozzaad(uj, &ujh);
}
if (micsoda == 3) {
String bbeolvas("");
int bm;
int bd;
getline(file, bbeolvas);
file >> bm;
file >> bd;
Basketball ujh(bbeolvas, bm, bd);
hozzaad(uj, &ujh);
}
}
std::cout << "OK" << std::endl;
listaz(uj);
file.close();
std::cout << "OK" << std::endl;
}
test4() expects to go out like:
還可以Kezes HC 21 50000還可以
將代碼縮短到絕對必要的位置:
if (micsoda == 1)
{
Handball ujh;
hozzaad(uj, &ujh);
} // at this point in code, your object ujh runs out of scope!!!
當對象超出范圍時,它會被銷毀(您會注意到是否在類的析構函數中添加了一些輸出語句...),並且指向該對象的任何指針都將變為無效; 特別是,列表中的那些將變得無效(可以說是懸空的指針-或引用,可能會發生相同的情況)。 現在使用它們會導致不確定的行為 -這意味着任何事情都可能發生。 如果您不走運(或視情況而定走運),您的程序甚至會崩潰。
請注意,由於缺少代碼的重要部分,我假設您僅將指向對象的指針存儲在ListaElem
類中,但是很可能,因為要存儲的類是多態的...
但是,您需要的是對象的壽命比程序在if塊中的壽命更長。 假設我們針對現實生活中的場景,那么僅將對象移出if子句是不可能的,因為我們可能需要多個同類型的單個對象。 因此,您將動態創建對象。 但是,那么您還必須處理內存管理和所有權問題。 處理內存管理部分最容易的方法是使用智能指針。 所有權? 好吧,對我來說,假設列表是對象的唯一所有者似乎很合理,因此您可以:
class ListElem
{
std::unique_ptr<Team> m_data;
public:
ListElem(std::unique_ptr<Team> data) // accepting a unique_ptr already here indicates
// clearly that the item will grab ownership
: m_data(std::move(data)) // unique_ptr is only movable, not copiable!
{ }
}
然后,您可以將上面的代碼更改為:
if (micsoda == 1)
{
int n, m; // sample data
hozzaad(uj, std::make_unique<Team>(n, m); // arguments are passed directly to
// the constructor of class Team
}
好的,您不允許使用STL。 那么您將自己編寫智能指針以及make_unique
並move
模板函數(就像您對list和string所做的那樣)。 在cppreference上,您可以找到一個示例實現,例如std::make_unique
。 不要只是復制/粘貼代碼,而是先了解它,最好自己重新編寫它,否則您將不會學任何東西(上面的代碼也是如此)。 或者,您可能會問您的老師,她/他是否在智能指針的STL方面例外。
最終建議:在連續內存上進行操作通常比在整個系統RAM上可能分布的內存上進行操作要快得多。 因此,您可以考慮重新實現std::vector
而不是std::list
。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.