Visualizzazione dei risultati da 1 a 4 su 4

Discussione: C++ stringhe vuote

  1. #1

    C++ stringhe vuote

    Ciao a tutti, mi sono appena registrata sul forum.
    Ho scritto un programma in C++, che salva dei dati letti da file in variabili inizializzate in una classe tramite una funzione di tipo 'set' ad esempio. Le variabili sono sia stringhe che interi e float. Se nella funzione che setta le variabili inserisco una stampa per controllare che la copia sia avvenuta, la stampa è corretta. Se, invece, dichiaro una nuova funzione specifica, di tipo 'print', per verificare il contenuto delle variabili, i valori numerici sono corretti, ma le stringhe sono vuote.
    Questo problema mi era già successo e non riesco a capire perchè: forse sbaglio a copiare il contenuto delle stringhe?
    Ho provato ad allegare lo zip ma è troppo grande, carico il file da leggere, se avete voglia di dare un'occhiata sareste gentilissimi.

    La descrizione del programma è la seguente.
    Si legge un file (studentInfo.txt) in cui ogni riga contiene un nome, un cognome e un certo numero di interi; per ogni persona chiamo una classe (vettManipClass) che calcola massimo, minimo, deviazione standard e media del gruppo di interi relativi a quella persona. Nel main, ho controllato che i valori calcolati sono corretti. Poi, vorrei memorizzare ogni nome, cognome e valori calcolati, utilizzando due classi composte: Student, che contiene i 4 valori, nome e cognome, e Register, che contiene un vettore di classi Student.
    Nel main c'è una sorta di menù che permette all'utente di scegliere cosa stampare a video (nome, cognome e media relativa, etc...)
    Nel'output, ogni volta che provo a stampare le stringhe nomi e cognomi, sono vuote.

    main.cpp
    codice:
    #include <iostream>
    #include <stdlib.h>
    #include <fstream>
    #include <sstream>
    #include <string>
    #include "C:/Users/vettManipClass.hpp"
    #include "Student.hpp"
    #include "Register.hpp"
    using namespace std;
    
    
    int main()
    {
        string file_name; string line; string name; string surname; int n_exams; int val[20]; int i; int opt=0; int cont=0;
        string out_name; string new_name, new_surname; int voto; int flag;
    
    
        cout << "Insert the file name: ";
        cin >> file_name;
    
    
        ifstream myfile;
        myfile.open(file_name.c_str());
    
    
        if(!myfile) {
            cerr << "Error! The file " << file_name  << " doesn't exist.";
            exit(EXIT_FAILURE);
        }
        while(getline (myfile, line)) {
            istringstream is;
            is.str(line);
            is >> name >> surname >> n_exams;
            is.clear();
    
    
            getline (myfile, line);
            is.str(line);
            for(i=0; i<n_exams; i++) {
                is >> val[i];
            }
            is.clear();
    
    
    
    
            vettManipClass vettManipObject;
            vettManipObject.setNumAndVett(n_exams, val);
    
    
            Register registro;
            registro.add_student(name, surname, vettManipObject.maxFunct(), vettManipObject.minFunct(), vettManipObject.averageFunct(), vettManipObject.devFunct(), cont);
    
    
            cont++;
    
    
    
    
            }
        myfile.close();
    
    
        while(opt!=4) {
            cout << endl << "Please choose one of the following options :" << endl << "[1] Simple report" << endl << "[2] Detailed report" << endl << "[3] Check student" << endl << "[4] Quit" << endl;
            cin >> opt;
            switch (opt)         // THIS IS A MENU WHERE THE USER CHOOSES THE OUTPUT
            {
            case 1 : {
    
    
                Register registro;
                registro.print_student(cont);
                break; }
    
    
            case 2 : {
    
    
                cout << "Insert output file name: "; cin >> out_name;
                Register registro;
                registro.print_file(out_name);
                break; }
    
    
            case 3 : {
                cout << "Insert name surname grade : ";
                cin >> new_name >> new_surname >> voto;
    
    
                Register registro;
                flag = registro.ricerca(new_name, new_surname, voto);
                switch (flag)
                {
                case 0:
                    cout << endl << "ERROR : no student named " << new_name << ' ' << new_surname << " was found !" << endl;
                    break;
                case 1:
                    cout << endl << "no" << endl;
                    break;
                case 2:
                    cout << endl << "ok" << endl;
                    break;
                }
                break; }
    
    
    
    
            }
        }
    
    
        cout << endl << "END OF THE PROGRAM" << endl;
        return 0;
    }

    Register.hpp

    codice:
    #define REGISTER_H#define MAX_STUDENTS 50
    #include "Student.hpp"
    using namespace std;
    
    
    class Register
    {
        public:
            Register();
            virtual ~Register();
    
    
            void add_student(string, string, int, int, float, float, int);
            void print_student(int);
            void print_file(string);
            int ricerca(string, string, int);
    
    
        protected:
        private:
            Student vett[MAX_STUDENTS];
            int j; int lim; string _out_name;
            int _flag; string _new_name; string _new_surname; int _voto;
    };
    
    
    #endif // REGISTER_H

    Register.cpp

    codice:
    #include "Register.hpp"#include "Student.hpp"
    #include <string>
    #include <iostream>
    using namespace std;
    
    
    Register::Register()
    {
        //ctor
    }
    
    
    Register::~Register()
    {
        //dtor
    }
    void Register::add_student(string _nome, string _cognome, int _massimo, int _minimo, float _media, float _deviazione, int _cont)
    {
        vett[_cont] = Student(_nome, _cognome, _massimo, _minimo, _media, _deviazione);
        //cout << endl << "cont = " << _cont << ' ' << _nome << ' ' << _cognome << ' ' << _massimo << ' ' << _minimo << ' ' << _media << ' ' << _deviazione << endl;
    }
    void Register::print_student(int lim)
    {
        for(j=0; j<lim; j++)
            vett[j].Student::print();
    }
    void Register::print_file(string _out_name)
    {
        for(j=0; j<lim; j++)
            vett[j].Student::printOnFile(_out_name);
    }
    int Register::ricerca(string _new_name, string _new_surname, int _voto)
    {
        _flag = 0;
        for(j=0; j<lim && _flag==0; j++) {
            _flag = vett[j].Student::controllo(_flag, _new_name, _new_surname, _voto);
        }
        return _flag;
    }

    Student.hpp

    codice:
    #ifndef STUDENT_H#define STUDENT_H
    #include <string>
    using namespace std;
    
    
    class Student
    {
        public:
            Student();
            Student(string, string, int, int, float, float);
            virtual ~Student();
    
    
            void print();
            void printOnFile(string);
            int controllo(int, string, string, int);
    
    
            string nome; string cognome; int massimo; int minimo; float media; float deviazione;
    
    
        protected:
        private:
    
    
            int k; char c;
            string _out_name;
            int FLAG; string NAME; string SURNAME; int VOTO;
    
    
    };
    
    
    #endif // STUDENT_H

    Student.cpp

    codice:
    #include "Student.hpp"#include <string>
    #include <iostream>
    #include <iomanip>
    #include <ctype.h>
    #include <fstream>
    using namespace std;
    
    
    Student::Student()
    {
        //ctor
    }
    
    
    Student::~Student()
    {
        //dtor
    }
    Student::Student(string _nome, string _cognome, int _massimo, int _minimo, float _media, float _deviazione)
    {
        nome = _nome;
        cognome = _cognome;
        massimo = _massimo;
        minimo = _minimo;
        media = _media;
        deviazione = _deviazione;
    }
    void Student::print()
    {
        cout << endl;
    
    
        for(k=0; nome[k]!='\0'; k++) {
            c = toupper(nome[k]);
            cout << c;
        }
        cout << ' ';
        for(k=0; cognome[k]!='\0'; k++) {
            c = toupper(cognome[k]);
            cout << c;
        }
        cout << ' ';
        cout << setprecision(4) << media << endl;
    
    
    }
    void Student::printOnFile(string _out_name)
    {
        ofstream fout;
        fout.open(_out_name.c_str(), ios::app);
        fout << nome << ' ' << cognome << ' ' << massimo << ' ' << minimo << ' ' << media << ' ' << setprecision(3) << deviazione << endl;
        fout.close();
    
    
    }
    int Student::controllo(int FLAG, string NAME, string SURNAME, int VOTO)
    {
        if(nome==NAME && cognome==SURNAME) {
            FLAG = 1;
            if(VOTO<=media)
                FLAG = 2;
        }
        return FLAG;
    }
    File allegati File allegati
    Ultima modifica di cristina1996; 19-04-2017 a 11:55

  2. #2
    Utente di HTML.it L'avatar di boots
    Registrato dal
    Oct 2012
    Messaggi
    1,626
    C'è voluto un po', ma alla fine credo di aver capito il problema: Ridichiari sempre registro. In questo modo lo sovrascrivi perdendo le stringhe (non l'oggetto, ma il "valore" ) visto che sono allocate nell'heap al contrario degli int che sono nello stack.
    codice:
    main (){
      ...
     while(getline (myfile, line)) {
          ...
          Register registro; // Lo dichiari ad ogni ciclo
          vettManipClass vettManipObject;
     }
    ...
     case 1 : {
                Register registro; // Lo ridichiari
                registro.print_student(cont);
                break; }
     case 2 : {
                cout << "Insert output file name: "; cin >> out_name;
                Register registro;  // Lo ridichiari anche qua
                registro.print_file(out_name);
                break; }
            case 3 : {
                cout << "Insert name surname grade : ";
                cin >> new_name >> new_surname >> voto;
                Register registro; // e qui
    }
    Dichiarali una sola volta all'inizio del main (non dentro un ciclo) e basta.

    inoltre , non ti conviene tener traccia del numero degli studenti dentro Register?

  3. #3
    Quote Originariamente inviata da boots Visualizza il messaggio
    C'è voluto un po', ma alla fine credo di aver capito il problema: Ridichiari sempre registro. In questo modo lo sovrascrivi perdendo le stringhe (non l'oggetto, ma il "valore" ) visto che sono allocate nell'heap al contrario degli int che sono nello stack.

    Dichiarali una sola volta all'inizio del main (non dentro un ciclo) e basta.
    Oddio grazie!!! Che stupida... è vero. E ho aggiustato anche il contatore degli elementi...
    Grazie mille!!! Ti adoro !! Sei gentilissimo, grazie per esserti preso la briga di aiutarmi.
    Ti pagherei volentieri un caffè!
    Mi sono scervellata per giorni, sei un genio, grazie infinite!
    Ultima modifica di cristina1996; 19-04-2017 a 14:49

  4. #4
    Utente di HTML.it L'avatar di boots
    Registrato dal
    Oct 2012
    Messaggi
    1,626
    Di niente ...

Tag per questa discussione

Permessi di invio

  • Non puoi inserire discussioni
  • Non puoi inserire repliche
  • Non puoi inserire allegati
  • Non puoi modificare i tuoi messaggi
  •  
Powered by vBulletin® Version 4.2.1
Copyright © 2024 vBulletin Solutions, Inc. All rights reserved.