terminate called after throwing an instance... ERROR!

I need help with this code. It is only a part of my project but i think that this is the usefull piece to understand the problem.
The error is:
terminate called after throwing an instance of 'std::out_of_range'
what(): basic_string::substr




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
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
 #include "ControlClass.h"


void ControlClass::readAnswers (string filename1)
{
    ifstream fin;
    string line,str(" "), id, text;
    istringstream is;




    fin.open(filename1.c_str());
    if (!fin.is_open())
    {
        cerr<<"Errore nell'apertura file risposte!"<<endl;
    }

    while(getline(fin,line))
    {
        //verificare presenza di uno spazio tra id e testo
        size_t found = line.find(str);
        if(found!= string::npos)
        {
            //se la stringa è conforme ai canoni sintattici, memorizzo in una mappa
            is.str(line);
            is>>id;
            text = line.substr(line.find( " "));
            is.clear();
            AnswerClass answer(id, text);
            _mapAns[id]=answer;


        }
        else
        {
            cout<<"Errore: file risposte non rispetta i canoni sintattici"<<endl;
            //bloccare il programma---> capire come fare;
        }
    }
    fin.close();
}

/*void ControlClass::print_mapAns()
{
     map<string, AnswerClass> :: iterator p;
    for (p = _mapAns.begin(); p != _mapAns.end(); p++)
        cout<<p->first<<" "<<p->second<<endl;

}*/

void ControlClass::readQuestions(string filename2)
{

    ifstream fin;
    string line, str1, id_q, id_link_a,text,id_link_q;
    int n_answer, i;
    istringstream is;
    QuestionClass question;


    fin.open(filename2.c_str());
    if (!fin.is_open())
    {
        cerr<<"Errore nell'apertura file risposte!"<<endl;
    }
    //controllo correttezza del formato; se non pervenuto non conviene procedere con la memorizzazione degli elementi in gioco;
    while(getline(fin,line))
    {
        is.str(line);
        is>>str1>>id_q>>n_answer;
        text= line.substr(line.find( " "));
        is.clear();

        if ((str1 == "[Q]") && n_answer>1) //n_answer >1 non va bene per due ragioni: 1. è un errore concettuale perchè non ci possono essere zero o una risposta
            //                                          2. se il terzo campo non fosse un intero ma una stringa (quindi non conforme al formato) n_answer verrebbe salvato come zero;
        {
            QuestionClass question(id_q, text);
            _mapQuest[id_q]=question;

            for(i=0; i<n_answer; i++)
            {
                getline(fin, line1);
                is.str(line1);
                is>>str1>>id_link_a;
                text= line.substr(line.find( " "));
                is.clear();
                if(str1=="[A]")
                {
                    _mapQuest[id_q]._linkedAns.push_back(id_link_a);
                    is.str(text);

                    while (is>>id_link_q)
                    {
                        _mapAns[id_link_a]._linkedQuest.push_back(id_link_q);
                    }
                    is.clear();




                }
                else
                {
                    cout<<"Errore: il file di domande non rispetta il formato predefinito!"<<endl;
                    //capire come uscire dal programma;
                }

            }



        }
        else
        {
            cout<<"Errore: il file di domande non rispetta il formato predefinito!"<<endl;
            //capire come uscire dal programma;
        }
    }

    fin.close();
}


void ControlClass::print_mapQuest()
{
     map<string, QuestionClass> :: iterator p;
    for (p = _mapQuest.begin(); p != _mapQuest.end(); p++)
        cout<<p->first<<" "<<p->second<<endl;

}

text= line.substr(line.find( " "));
What happens if there are no spaces in the line? Remember if find() fails it returns the largest value that can be held in a std::string::size_type.
Last edited on
it's very strange because this costruct works in the function readAnswers, while in readQuestions not. It's true what you say but i think that it could not work also in the first function...
It's true what you say but i think that it could not work also in the first function...

Correct, using the find() function without checking if it succeeded is dangerous and can cause run time errors like you're seeing. You really should always check that the find() is successful.



Topic archived. No new replies allowed.