read .txt file via fstream into struct with array member

Hello there. I just started learning C++, so I am a bloody beginner. Please bare with me! :)

I've got a task for university, and I'm struggling to work with fstream and structs.

The task is, to fill a struct with a .txt file...
The struct looks like that:
struct schokolade
{
char name[20];
int gewicht;
int zutat_id[5];
int menge_in_prozent[5];
};

and the .txt file looks like that:

vollmilch_mandel <-name
100 <- weight
5 <- amount of ingredients
kakao 34 <- ingredient name + how much of it is in the chocolate
kakaobutter 10
milchpulver 20
zucker 28
mandeln 8

marzipan
100
3
kakao 50
zucker 25
marzipan 25

keksschoki
100
5
kakao 40
mandeln 7
kakaobutter 8
zucker 30
keks 15

However, the task description says that I have to change the name of the ingredient into an ID which I do not really get.

Moreover, I am struggling to understand, how I am able to put the .txt into that struct, since the setup of both is completely different, e.g. the name of the ingredient is a string and I have to put it in an int array.

Within my code, there is another file and another struct, namely "zutaten.txt", that works perfectly fine. I am just having problems with the other file.
Thats what I got so far:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
  #include <iostream>
#include <fstream>
#include <string>
using namespace std;

struct schokolade               //struct for schoki.txt
{
    string name;
    int gewicht;
    int zutat_id[5];
    int menge_in_prozent[5];
};

struct zutat                    //struct for zutaten.txt
{
    string name;
    float preis_pro_gramm;
};

int main()
{
    zutat feld[7];              //Reading of "zutaten.txt"
    int i = 0;
    ifstream file;
    file.open("zutaten.txt");
    if(file.is_open()){

        for(i; i<7; i++)
        {

            file >> feld[i].name;
            file >> feld[i].preis_pro_gramm;
        }

        file.close();
    }
    else{
        cout << "Datei Konnte nicht geöffnet werden!" << endl;
        return 0;
    }

    schokolade feld_2[3];
    int j=0;
    int k=0;

     for(j; j<3; j++)
    {
        for(int i=0; i<5; i++)
        {
        feld_2[j].zutat_id[i] = 0;
        feld_2[j].menge_in_prozent[i] = 0;
        }
    }

    for(int j=0; j<3; j++)
    {
        for(int i=0; i<5; i++)
        {

        feld_2[j].zutat_id[i] = i;      //Give an ID for the ingredient?
        }
    }


    ifstream file_2;                    //Reading of file "schoki.txt"
    file.open("schoki.txt");
    if(file.is_open()){
        for(int j=0; j<3; j++)
        {

        file_2 >> feld_2[j].name;
        file_2 >> feld_2[j].gewicht;
        file_2 >> feld_2[j].menge_in_prozent[5];
        }

    file_2.close();
    }else{
        cout << "Datei Konnte nicht geöffnet werden!" << endl;
        return 0;
    }

    for(int i=0; i<7; i++)  // just to test, if the fstream worked properly
    {
        cout << "Name: " << feld[i].name <<" Preis pro Gramm: " << feld[i].preis_pro_gramm << "\n";
    }
    for(int j=0; j<3; j++)
    {
        for (int i=0; i<7; i++)
        {
            cout << "Name: " << feld_2[j].name <<" Gewicht: " << feld_2[j].gewicht <<" ID: " << feld_2[j].zutat_id[i] <<" Menge in Prozent: " << feld_2[j].menge_in_prozent << "\n";
        }
    }
    return 0;
}


Sry for the German in there, and the wall of text. But I really have no clue, on how to solve that problem. :(
You seem to be trying to read two files, please post a small sample of both files, don't forget to identify which file is which and please post the file contents inside code tags.


By the way this section looks incorrect:

1
2
3
   ifstream file_2;                    //Reading of file "schoki.txt"
    file.open("schoki.txt");
    if(file.is_open()){


Shouldn't you be opening and testing file_2 instead of file?

The first file is "zutaten.txt" that works fine.

The other file is "schoki.txt" which does not work at all.

It looks like that:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
vollmilch_mandel
100
5
kakao 34
kakaobutter 10
milchpulver 20
zucker 28
mandeln 8

marzipan
100
3
kakao 50
zucker 25
marzipan 25

keksschoki
100
5
kakao 40
mandeln 7
kakaobutter 8
zucker 30
keks 15
Here's how you'd read such a file using standard library containers like std::map and std::vector. If you HAVE to use C-style arrays you can try and reverse engineer this, I'm sorry it's going to take me too long to go back to C-style anything: The key is that the data is non-uniform and the information about the non-uniformity is on the 3rd line of each struct object. So once you can extract that information and rest of it is fairly simple:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
#include <iostream>
#include <string>
#include <map>
#include <fstream>
#include <sstream>
#include <vector>
#include <algorithm>

struct Chocolate
{
    std::string m_name;
    double m_weight;
    int m_ingred_num;
    std::map<std::string, double> m_ingred_compo;
};

std::ostream& operator << (std::ostream& os, const Chocolate& c)
{
    os << c.m_name << " " << c.m_weight << " " << c.m_ingred_num << '\n';
    for (auto& elem : c.m_ingred_compo)
    {
        os << elem.first << " " << elem.second << '\n';
    }
    return os;
}

int main()
{
    std::ifstream infile ("D:\\input.txt");
    std::vector<Chocolate> recipes;
    while(infile)
    {
        Chocolate temp;
        {
            int temp_int{};
            infile >> temp.m_name >> temp.m_weight >> temp_int;
            int i{};
            std::string temp_name;
            double temp_choco;
            while ((i < temp_int) && infile >> temp_name >> temp_choco)
            {
                temp.m_ingred_compo[temp_name] = temp_choco;
                i++;
            }
            temp.m_ingred_num = temp_int;
            std::string line;
             if(infile)
            {
                recipes.push_back(std::move(temp));
            }
            getline(infile, line);

        }
    }

    for (auto& elem : recipes)
    {
        std::cout << elem << '\n';
    }
}

Output
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
vollmilch_mandel 100 5
kakao 34
kakaobutter 10
mandeln 8
milchpulver 20
zucker 28

marzipan 100 3
kakao 50
marzipan 25
zucker 25

keksschoki 100 5
kakao 40
kakaobutter 8
keks 15
mandeln 7
zucker 30


Last edited on
Thank you SO much! That helped me a lot!
Topic archived. No new replies allowed.