3 votes

c++ comment lire un flux jusqu'à la fin de la ligne

Je veux lire une entrée comme celle-ci à partir du fichier

sphère 3 2 3 4
pyramide 2 3 4 12 3 5 6 7 3 2 4 1 2 3
rectangle 2 3 4 1 9 12

Je veux faire quelque chose comme ceci

char name[64];  
int arr[12];  
ifstream file (..);  
while(file)  
{   
file >> name;  
    while( //reach end of line) 
        file >> arr[i]
}

Comme vous pouvez le voir, je ne sais pas combien d'entiers seront saisis, c'est pourquoi je veux m'arrêter à la nouvelle ligne. Je l'ai fait avec getline, puis en divisant la ligne, mais on m'a dit que cela ne pouvait être fait qu'avec l'opérateur >>.

Note : Je ne peux pas utiliser std::string o std::vector .

3voto

Dietmar Kühl Points 70604

La version simple est d'utiliser un manipulateur similaire à std::ws mais au lieu de sauter tous les espaces blancs, le paramètre std::ios_base::failbit lorsqu'une nouvelle ligne est rencontrée. Ce manipulateur serait alors utilisé pour, au lieu de sauter les espaces blancs, sauter implicitement les espaces blancs autres que les nouvelles lignes. Par exemple (le code n'est pas testé mais je pense que quelque chose comme ceci avec les bugs et les erreurs de compilation enlevés devrait fonctionner) :

std::istream& my_ws(std::istream& in) {
    std::istream::sentry kerberos(in);

    while (isspace(in.peek())) {
        if (in.get() == '\n') {
            in.setstate(std::ios_base::failbit);
        }
    }
    return in;
}
// ...
char name[64];
int  array[12];
while (in >> std::setw(sizeof(name)) >> name) {  // see (*) below
    int* it = std::begin(array), end = std::end(array);
    while (it != end && in >> my_ws >> *it) {
        ++it;
    }
    if (it != end && in) { deal_with_the_array_being_full(); }
    else {
        do_something_with_the_data(std::begin(array), it);
        if (!in.eof())  { in.clear(); }
    }
}

Je pense personnellement que le devoir demandait de lire les valeurs dans le fichier char puis de les convertir en utilisant atoi() o strol() . Je pense que ce serait une solution ennuyeuse à l'exercice.

(*) Jamais même pas dans un exemple de code, utilisez l'opérateur d'entrée formatée avec une balise char tableau array sans en fixant également la taille maximale autorisée ! La taille peut être définie en paramétrant l'attribut width() en utilisant, par exemple, le manipulateur. std::setw(sizeof(array)) . Si le width() es 0 lors de l'utilisation de l'opérateur de saisie formatée avec un char un nombre arbitraire de caractères sans espace est lu. Cela peut facilement déborder le tableau et devenir un problème de sécurité ! Essentiellement, c'est la façon C++ d'épeler la fonction C gets() (qui est maintenant retiré des bibliothèques standard C et C++).

1voto

Edgar Rokyan Points 1335

Je suppose que vous pouvez utiliser coup d'œil méthode :

while (file)
{
    file >> name;
    int i = 0;
    while(file.peek() != '\n' && file.peek() != EOF) {
        file >> arr[i++];
    }
}

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X