Marc Boyer wrote:je redécouvre peut-être la roue, mais j'ai un problème pour
faire en C++ un truc que je savais bien faire en C.
Sur ma ligne de commande, soit l'utilisateur passe un nom
de fichier, et il faut lire dans ce fichier, soit il ne
dit rien, et on lit dans cin.
Mais comment faire ?
Je connais cin, fistream, mais entre le fait qu'on ne peut pas
copier de ostream, le RAII, la seule solution que je vois,
c'est de déclarer un pointeur
istream *in;
ce qui va être lourd à utiliser.
La solution habituelle, c'est quelque chose du genre :
if ( argc == 1 ) {
process( std::cin ) ;
} else {
for ( int i = 1 ; i < argc ; ++ i ) {
if ( strcmp( argv[ i ], "-" ) ) {
process( std::cin ) ;
} else {
std::ifstream src( argv[ i ] ) ;
if ( ! src ) {
std::cerr << "Cannot open " << argv[ i ] << std::endl ;
} else {
process( src ) ;
}
}
}
}
Si (comme moi), tu utilises une classe pour parser la ligne de
commande, la plus facile, c'est qu'elle se présente comme un
std::vector avec les noms de fichiers, après avoir enlevé
les options. Ensuite, tu fais comme ci-dessus, sauf avec ce
vecteur, à la place de argv.
Enfin, si tu t'y connais avec les flux, ce n'est pas trop
difficile d'écrire un flux qui fait le tous.
Marc Boyer wrote:
je redécouvre peut-être la roue, mais j'ai un problème pour
faire en C++ un truc que je savais bien faire en C.
Sur ma ligne de commande, soit l'utilisateur passe un nom
de fichier, et il faut lire dans ce fichier, soit il ne
dit rien, et on lit dans cin.
Mais comment faire ?
Je connais cin, fistream, mais entre le fait qu'on ne peut pas
copier de ostream, le RAII, la seule solution que je vois,
c'est de déclarer un pointeur
istream *in;
ce qui va être lourd à utiliser.
La solution habituelle, c'est quelque chose du genre :
if ( argc == 1 ) {
process( std::cin ) ;
} else {
for ( int i = 1 ; i < argc ; ++ i ) {
if ( strcmp( argv[ i ], "-" ) ) {
process( std::cin ) ;
} else {
std::ifstream src( argv[ i ] ) ;
if ( ! src ) {
std::cerr << "Cannot open " << argv[ i ] << std::endl ;
} else {
process( src ) ;
}
}
}
}
Si (comme moi), tu utilises une classe pour parser la ligne de
commande, la plus facile, c'est qu'elle se présente comme un
std::vector avec les noms de fichiers, après avoir enlevé
les options. Ensuite, tu fais comme ci-dessus, sauf avec ce
vecteur, à la place de argv.
Enfin, si tu t'y connais avec les flux, ce n'est pas trop
difficile d'écrire un flux qui fait le tous.
Marc Boyer wrote:je redécouvre peut-être la roue, mais j'ai un problème pour
faire en C++ un truc que je savais bien faire en C.
Sur ma ligne de commande, soit l'utilisateur passe un nom
de fichier, et il faut lire dans ce fichier, soit il ne
dit rien, et on lit dans cin.
Mais comment faire ?
Je connais cin, fistream, mais entre le fait qu'on ne peut pas
copier de ostream, le RAII, la seule solution que je vois,
c'est de déclarer un pointeur
istream *in;
ce qui va être lourd à utiliser.
La solution habituelle, c'est quelque chose du genre :
if ( argc == 1 ) {
process( std::cin ) ;
} else {
for ( int i = 1 ; i < argc ; ++ i ) {
if ( strcmp( argv[ i ], "-" ) ) {
process( std::cin ) ;
} else {
std::ifstream src( argv[ i ] ) ;
if ( ! src ) {
std::cerr << "Cannot open " << argv[ i ] << std::endl ;
} else {
process( src ) ;
}
}
}
}
Si (comme moi), tu utilises une classe pour parser la ligne de
commande, la plus facile, c'est qu'elle se présente comme un
std::vector avec les noms de fichiers, après avoir enlevé
les options. Ensuite, tu fais comme ci-dessus, sauf avec ce
vecteur, à la place de argv.
Enfin, si tu t'y connais avec les flux, ce n'est pas trop
difficile d'écrire un flux qui fait le tous.
Jean-Marc Bourguet wrote:Marc Boyer writes:Sur ma ligne de commande, soit l'utilisateur passe un nom de
fichier, et il faut lire dans ce fichier, soit il ne dit rien, et on
lit dans cin.
[...]Il y a un truc ?
rdbuf
C'est curieux, mais je ne me suis jamais servi de rdbuf dans ce
cas-là.
Si on veut s'amuser à changer le streambuf de std::cin,
Jean-Marc Bourguet wrote:
Marc Boyer <Marc.Boyer@enseeiht.yahoo.fr.invalid> writes:
Sur ma ligne de commande, soit l'utilisateur passe un nom de
fichier, et il faut lire dans ce fichier, soit il ne dit rien, et on
lit dans cin.
[...]
Il y a un truc ?
rdbuf
C'est curieux, mais je ne me suis jamais servi de rdbuf dans ce
cas-là.
Si on veut s'amuser à changer le streambuf de std::cin,
Jean-Marc Bourguet wrote:Marc Boyer writes:Sur ma ligne de commande, soit l'utilisateur passe un nom de
fichier, et il faut lire dans ce fichier, soit il ne dit rien, et on
lit dans cin.
[...]Il y a un truc ?
rdbuf
C'est curieux, mais je ne me suis jamais servi de rdbuf dans ce
cas-là.
Si on veut s'amuser à changer le streambuf de std::cin,
Marc Boyer writes:
Le rdbuf renvoyé par un fstream, c'est un pointeur vers un
membre.
Mais le dit membre pourrait avoir un champs interne qui lui
dit qu'il est partagé, incrémenté à chaque appel à rdbuf(
streambuf* ).
Ceci dit, quand deux fstream partagent le même streambuf,
s'il n'y a pas de notion de partage, c'est le premier
destructeur appelé qui ferme le flux.
Est-ce que cela signifie que le code suivant est correct,
malgrès le non appel du destructeur de *ptr_file ?
ostream out;
ofstream* ptr_file ; // <<<=== ne manquait-il pas quelque chose ?
if (*ptr_file) {
out.rdbuf( ptr_file->rdbuf() );
}
Marc Boyer <Marc.Boyer@enseeiht.yahoo.fr.invalid> writes:
Le rdbuf renvoyé par un fstream, c'est un pointeur vers un
membre.
Mais le dit membre pourrait avoir un champs interne qui lui
dit qu'il est partagé, incrémenté à chaque appel à rdbuf(
streambuf* ).
Ceci dit, quand deux fstream partagent le même streambuf,
s'il n'y a pas de notion de partage, c'est le premier
destructeur appelé qui ferme le flux.
Est-ce que cela signifie que le code suivant est correct,
malgrès le non appel du destructeur de *ptr_file ?
ostream out;
ofstream* ptr_file ; // <<<=== ne manquait-il pas quelque chose ?
if (*ptr_file) {
out.rdbuf( ptr_file->rdbuf() );
}
Marc Boyer writes:
Le rdbuf renvoyé par un fstream, c'est un pointeur vers un
membre.
Mais le dit membre pourrait avoir un champs interne qui lui
dit qu'il est partagé, incrémenté à chaque appel à rdbuf(
streambuf* ).
Ceci dit, quand deux fstream partagent le même streambuf,
s'il n'y a pas de notion de partage, c'est le premier
destructeur appelé qui ferme le flux.
Est-ce que cela signifie que le code suivant est correct,
malgrès le non appel du destructeur de *ptr_file ?
ostream out;
ofstream* ptr_file ; // <<<=== ne manquait-il pas quelque chose ?
if (*ptr_file) {
out.rdbuf( ptr_file->rdbuf() );
}
Marc Boyer wrote:je redécouvre peut-être la roue, mais j'ai un problème
pour faire en C++ un truc que je savais bien faire en C.
Sur ma ligne de commande, soit l'utilisateur passe un nom
de fichier, et il faut lire dans ce fichier, soit il ne
dit rien, et on lit dans cin.
Mais comment faire ?
Je connais cin, fistream, mais entre le fait qu'on ne peut
pas copier de ostream, le RAII, la seule solution que je
vois, c'est de déclarer un pointeur
istream *in;
ce qui va être lourd à utiliser.
La solution habituelle, c'est quelque chose du genre :
if ( argc = 1 ) {
process( std::cin ) ;
} else {
for ( int i > if ( strcmp( argv[ i ], "-" ) ) {
process( std::cin ) ;
} else {
std::ifstream src( argv[ i ] ) ;
if ( ! src ) {
std::cerr << "Cannot open " << argv[ i ] << std::e ndl ;
} else {
process( src ) ;
}
}
}
}
Si (comme moi), tu utilises une classe pour parser la ligne
de commande, la plus facile, c'est qu'elle se présente comme
un std::vector avec les noms de fichiers, après avoir enlevé
les options. Ensuite, tu fais comme ci-dessus, sauf avec ce
vecteur, à la place de argv.
Sauf qu'il y a un problème de combinatoire: là tu présentes
deux appels valeurs possibles pour la liste de paramètres de
process, imbriqués dans 3 branches de if. Si on prend cin
*et* cout, ça fait 4, et aver cerr, 8.
Bon, c'est vrai qu'on peut jouer avec ?:.
process(option_cin?cin:file_in, option_cout?cout:file_out);Enfin, si tu t'y connais avec les flux, ce n'est pas trop
difficile d'écrire un flux qui fait le tous.
Heuh, non, pour le moment, on ne peut pas dire que je m'y
connaisse...
Marc Boyer wrote:
je redécouvre peut-être la roue, mais j'ai un problème
pour faire en C++ un truc que je savais bien faire en C.
Sur ma ligne de commande, soit l'utilisateur passe un nom
de fichier, et il faut lire dans ce fichier, soit il ne
dit rien, et on lit dans cin.
Mais comment faire ?
Je connais cin, fistream, mais entre le fait qu'on ne peut
pas copier de ostream, le RAII, la seule solution que je
vois, c'est de déclarer un pointeur
istream *in;
ce qui va être lourd à utiliser.
La solution habituelle, c'est quelque chose du genre :
if ( argc = 1 ) {
process( std::cin ) ;
} else {
for ( int i > if ( strcmp( argv[ i ], "-" ) ) {
process( std::cin ) ;
} else {
std::ifstream src( argv[ i ] ) ;
if ( ! src ) {
std::cerr << "Cannot open " << argv[ i ] << std::e ndl ;
} else {
process( src ) ;
}
}
}
}
Si (comme moi), tu utilises une classe pour parser la ligne
de commande, la plus facile, c'est qu'elle se présente comme
un std::vector avec les noms de fichiers, après avoir enlevé
les options. Ensuite, tu fais comme ci-dessus, sauf avec ce
vecteur, à la place de argv.
Sauf qu'il y a un problème de combinatoire: là tu présentes
deux appels valeurs possibles pour la liste de paramètres de
process, imbriqués dans 3 branches de if. Si on prend cin
*et* cout, ça fait 4, et aver cerr, 8.
Bon, c'est vrai qu'on peut jouer avec ?:.
process(option_cin?cin:file_in, option_cout?cout:file_out);
Enfin, si tu t'y connais avec les flux, ce n'est pas trop
difficile d'écrire un flux qui fait le tous.
Heuh, non, pour le moment, on ne peut pas dire que je m'y
connaisse...
Marc Boyer wrote:je redécouvre peut-être la roue, mais j'ai un problème
pour faire en C++ un truc que je savais bien faire en C.
Sur ma ligne de commande, soit l'utilisateur passe un nom
de fichier, et il faut lire dans ce fichier, soit il ne
dit rien, et on lit dans cin.
Mais comment faire ?
Je connais cin, fistream, mais entre le fait qu'on ne peut
pas copier de ostream, le RAII, la seule solution que je
vois, c'est de déclarer un pointeur
istream *in;
ce qui va être lourd à utiliser.
La solution habituelle, c'est quelque chose du genre :
if ( argc = 1 ) {
process( std::cin ) ;
} else {
for ( int i > if ( strcmp( argv[ i ], "-" ) ) {
process( std::cin ) ;
} else {
std::ifstream src( argv[ i ] ) ;
if ( ! src ) {
std::cerr << "Cannot open " << argv[ i ] << std::e ndl ;
} else {
process( src ) ;
}
}
}
}
Si (comme moi), tu utilises une classe pour parser la ligne
de commande, la plus facile, c'est qu'elle se présente comme
un std::vector avec les noms de fichiers, après avoir enlevé
les options. Ensuite, tu fais comme ci-dessus, sauf avec ce
vecteur, à la place de argv.
Sauf qu'il y a un problème de combinatoire: là tu présentes
deux appels valeurs possibles pour la liste de paramètres de
process, imbriqués dans 3 branches de if. Si on prend cin
*et* cout, ça fait 4, et aver cerr, 8.
Bon, c'est vrai qu'on peut jouer avec ?:.
process(option_cin?cin:file_in, option_cout?cout:file_out);Enfin, si tu t'y connais avec les flux, ce n'est pas trop
difficile d'écrire un flux qui fait le tous.
Heuh, non, pour le moment, on ne peut pas dire que je m'y
connaisse...