Write to a vector and save info to a file

3

Good! I am trying to implement the recommendation that @eferion made in a previous question: Read string and floats of a file to calculate weighted average in C ++

But the IDE throws me several errors. The code is as follows:

#include <iostream>
#include <stdlib.h>
#include <fstream>
#include <string>
#include <vector>

using namespace std;

int main(){

    // Nombre del programa
    cout << "\t\t Promedio Ponderado\n" << endl;

    int num_Mat;
    string nombre;

    // Solicita el numero de materias
    cout << "Ingrese el numero de materias\n";
    cin >> num_Mat;

    //Crea vectores para la variable Nombres
    vector <string> vNombres;

    // Creación del archivo
    ofstream fNombres;

   // Apertura y comprobación

    if ( !fNombres.open("Nombres.txt") ) {
        cout << "Error al intentar abrir el archivo Nombres" << endl;
    } else {

        // Loop para obtener el nombre de las materias y enviarlas al vector
        for (int i = 0; i < num_Mat; i++){
        cout << "Ingresa el nombre de la materia " << i+1 << endl; // "+1" porque no existe Materia 0
        cin >> vNombres[i] ;
        fNombres << vNombres[i] << endl;
        }
    }

    fNombres.close();                                // Cierra el archivo 1

    system("pause");
    return 0;
}

And it throws me the following errors:

  • error: could not convert 'fName.std :: basic_ofstream < _CharT, _Traits > :: open > (((const char *) "Names.txt"), std :: operator | ((std :: _ Ios_Openmode) 16u, (std :: _ Ios_Openmode) 32u)) 'from' void 'to' bool '|

  • error: in argument to unary! |

  • What am I doing wrong?

    Also, I saw in another question that to create a vector, first write the type of variable that will go inside it and then name it, instead here, first declares the vector and then choose the type of variable to use . Source: C ++ with vectors

    Is it the same in the end?

    Thank you very much in advance!

        
    asked by Germán Diego Guisasola Plejo 05.06.2017 в 22:56
    source

    2 answers

    4

    Family objects in the file stream std::basic_fstream as std::ifstream and std::ofstream have a conversion operator to a Boolean value: std::basic_fstream::operator bool that returns true if the flow does not He has mistakes.

    Therefore, your code can be written like this:

    if ( std::ofstream fNombres{"Nombres.txt"} ) {
        // ...
    } else {
        cout << "Error al intentar abrir el archivo Nombres" << std::endl;
    }
    

    You will not need to call fNombres.close() because the file closes automatically when you exit the if block.

    How does this work?

    In C ++ it is possible to declare variables in the body of an instruction if 1 , these variables will live throughout the block if and block else (if any). Once the variable is declared, it can be used as a value on the right side (known as RValue in English).

    Given the existence of the Boolean conversion operator, fNombres will be evaluated as a condition (as if it were a Boolean), if the file could be opened it will not contain errors and will enter the body of if .

    Why does not it work for you?

      

    error: could not convert 'fNombres.std::basic_ofstream<_CharT, _Traits>::open >(((const char*)"Nombres.txt"), std::operator|((std::_Ios_Openmode)16u, (std::_Ios_Openmode)32u))' from 'void' to 'bool'

    The error you receive tells you that you can not convert from void to bool . This is because the function you use in the condition ( std::basic_fstream::open ) has a return type void , this type can not be evaluated as Boolean condition, but the compiler tries, fails, and complains:

      

    error: no puedo convertir 'fNombres.open("Nombres.txt") de 'void' a 'bool'

    void is not deniable.

      

    error: in argument to unary !

    The other error you receive is when you try to apply the unary operator of denial ( ! ) on a non-deniable type.

    The unary deny operator ( ! ) denies the Boolean value of a boolean expression or a boolean-convertible expression. C ++ offers implicit conversions to Boolean for numeric expressions (being 0 considered false and anything other than 0 considered true) but void is one of the types that can not be evaluated as Boolean.

    It's not all ...

    Once the compile-time errors have been corrected, the program will fail you at runtime, the response from Mario Rodríguez perfectly explain the mistakes you will find, take a look.

    1 Also in the statement switch and while

        
    answered by 06.06.2017 / 15:19
    source
    1

    The error is found in checking whether the file has been opened correctly. In that case open does not return a Boolean value, so you can change it to a function that does return what you need, such as:

    fNombres.open("Nombres.txt", ios::out);
    

    And then, to check if it could be opened (and not try to read from a nonexistent file) is_open :

    if ( !fNombres.is_open() ) { ... }
    

    In addition, the code that you pose will give you some more problems when adding elements to the vector, since you are trying to access positions that do not yet exist in it. More specifically:

    cin >> vNombres[i] ;
    

    To be able to do that before you must initialize the vector with as many positions as number of subjects to be included later.

    vector <string> vNombres(num_Mat,"");
    
        
    answered by 05.06.2017 в 23:51