IdentifiantMot de passe
Loading...
Mot de passe oubli� ?Je m'inscris ! (gratuit)
logo

FAQ C++Consultez toutes les FAQ

Nombre d'auteurs : 34, nombre de questions : 368, derni�re mise � jour : 14 novembre 2021  Ajouter une question

 

Cette FAQ a �t� r�alis�e � partir des questions fr�quemment pos�es sur les forums de http://www.developpez.com et de l'exp�rience personnelle des auteurs.

Je tiens � souligner que cette FAQ ne garantit en aucun cas que les informations qu'elle propose sont correctes ; les auteurs font le maximum, mais l'erreur est humaine. Cette FAQ ne pr�tend pas non plus �tre compl�te. Si vous trouvez une erreur ou si vous souhaitez devenir r�dacteur, lisez ceci.

Sur ce, nous vous souhaitons une bonne lecture.

SommaireLes cha�nes de caract�res : std::string (28)
pr�c�dent sommaire suivant
 

Le C++ standard poss�de son propre type cha�ne de caract�res : std::string. Celui-ci est d�clar� dans l'en-t�te standard <string>.

Code c++ : S�lectionner tout
1
2
3
4
5
6
7
8
9
10
#include <iostream> // pour std::cout 
#include <string>   // pour std::string 
  
int main() 
{ 
    std::string message = "Hello"; // cr�ation de la cha�ne "Hello" 
    message += " World !";         // concat�nation de " Word !" 
  
    std::cout << message << '\n';  // affichage de "Hello World !" 
}
string est le type cha�ne de caract�res standard du langage C++. Il est donc judicieux de l'utiliser en priorit� sur les char * qui sont h�rit�s du langage C. Pour plus de d�tails � ce sujet, vous pouvez lire Quels sont les avantages de std::string par rapport � char * ?.

Mis � jour le 19 octobre 2004 Aurelien.Regat-Barrel

Au del� du simple conteneur de caract�res, string est aussi et avant tout l'interface cha�ne de caract�res de la biblioth�que standard. Autrement dit en utilisant string vous b�n�ficiez des tr�s nombreuses autres fonctionnalit�s de la biblioth�que standard, ce qui est plus d�licat avec les char *.
Par exemple, il est possible de lire une ligne d'un fichier sans avoir � se pr�occuper de sa taille.
Un travail important de gestion et de v�rification est fait en toute transparence, ce qui rend le code plus maintenable. string est donc beaucoup plus simple et s�re d'utilisation que les nombreuses fonctions utilisant les char *.

Mis � jour le 19 octobre 2004 Aurelien.Regat-Barrel

Programmer en utilisant std::string est incontestablement plus rapide, plus lisible et plus s�r que de programmer en utilisant les antiques char*.
Si votre but est d'�crire un programme qui marche et qui soit facile � maintenir, utiliser string est un bien meilleur choix. Il est en effet tentant de dire qu'utiliser les char* fait surtout planter le programme plus vite.
Il faut aussi relativiser la possible lenteur de string par le fait que l'�cart est tr�s souvent sans cons�quence pour l'utilisateur.
M�me si lire et afficher une cha�ne de caract�res est deux fois plus lent avec les string qu'avec les char*, l'�cart est dans ce cas d�risoire voire non mesurable.
N�anmoins, il est des cas o� une application manipule un tr�s grand nombre de cha�nes de caract�res, et on peut alors, � juste titre, se poser la question.
La r�ponse n'est pas �vidente. Tout d'abord, le premier point en faveur des string est que celles-ci connaissent en permanence leur longueur (fonction size() ou length()), qui n'a donc pas besoin d'�tre calcul�e, contrairement aux char* ou il faut syst�matiquement effectuer un appel � strlen().
Ainsi, plus la longueur des cha�nes manipul�es est importante, et plus string se r�v�lera performante vis � vis des char*.
Un autre point important concerne la mani�re dont sont g�r�es les char*.
Beaucoup de programmeurs ne veulent pas s'emb�ter et d�finissent g�n�ralement une taille commune � toutes leurs cha�nes de caract�res.

Code c++ : S�lectionner tout
1
2
3
4
5
6
7
8
9
#define MAX_SIZE 100 
  
void Exemple( void ) 
{ 
    char nom[ MAX_SIZE ]; 
  
    printf( "Veuillez entrer votre nom : " ); 
    fgets( stdin, nom, MAX_SIZE ); 
}
L� aussi, string est meilleur car non seulement le probl�me (in�vitable) de la fois o� cette taille limite sera atteinte ne se pose pas, mais aussi parce que ce code C provoque une perte plus ou moins importante de m�moire (typiquement, MAX_SIZE vaut 100 voire 1000, c'est-�-dire que m�me si une cha�ne ne comporte que 10 caract�res, elle occupera 100 ou 1000 octets en m�moire !).
La comparaison doit donc �tre faite avec une gestion dynamique de char*, chose laborieuse � g�rer en C et faite de mani�re transparente et s�re par string.
Enfin, il est difficile de g�n�raliser sur les string dans la mesure o� celles-ci sont sp�cifiques � un compilateur (et m�me souvent une version de compilateur) et ce qui est vrai pour une impl�mentation ne l'est pas forc�ment pour une autre (d'autant plus que la capacit� d'optimisation du compilateur entre aussi en jeu).
Ainsi, par exemple, la classe string de Visual C++ 6 impl�mente le Copy On Write (pas de copie r�elle de contenu entre 2 string, mais un partage via un comptage de r�f�rences) qui permet d'effectuer des affectations tr�s rapides entre string. La version 7 de ce compilateur n'impl�mente plus cette fonctionnalit� mais int�gre un petit buffer de 16 octets destin� � contenir directement les cha�nes de petite taille.
Cela permet de se passer d'allocation dynamique et donc d'augmenter les performances qui sont du coup �gales � celles d'un tableau de char (dans le cas de petites cha�nes).
La comparaison de performances entre string et char* est donc difficile, et elle ne peut �tre qu'au cas par cas.
Bien souvent, l'�cart de performance entre les deux est de l'ordre de quelques pour cent.
Vous l'aurez compris, la performance est loin d'�tre le seul crit�re, aussi faites confiance aux nombreux d�veloppeurs de talent qui ont d�velopp� le C++ et utilisez le type cha�nes de caract�res qui lui est propre : string.

Mis � jour le 19 octobre 2004 Aurelien.Regat-Barrel

std::string effectue en g�n�ral une allocation dynamique afin de stocker la cha�ne de caract�res. Cette allocation peut �chouer si la m�moire fait d�faut. Il faut donc �tre prudent avec l'utilisation de std::string et plus g�n�ralement des conteneurs de la STL lors de la gestion d'une exception std::bad_alloc.

Code c++ : S�lectionner tout
1
2
3
4
5
6
7
8
9
10
11
12
void Exemple() 
{ 
    try 
    { 
        // effectuer une allocation 
    } 
    catch ( std::bad_alloc & ) 
    { 
        // ATTENTION : utiliser std::string ou tout autre conteneur standard 
        // peut d�clencher une nouvelle exception std::bad_alloc 
    } 
}
C'est pour cela que la classe de base des exceptions std::exception n'utilise pas std::string pour sa fonction membre what() qui renvoie un message d�crivant l'exception. Il ne faut donc pas chercher � le faire lorsque l'on cr�e sa propre classe exception.

Mis � jour le 19 octobre 2004 Aurelien.Regat-Barrel

const char* et char const * ont la m�me signification : un pointeur sur un caract�re constant.
La r�gle est que le const s'applique toujours sur ce qui le pr�c�de. S'il n'y a rien avant, alors on inverse sa position avec ce qui est juste apr�s.
Utiliser const signifie qu'il ne faut pas modifier le(s) caract�re(s) r�f�renc�(s) par le pointeur.
Donc, typiquement, une fonction qui prend un char* d�clare qu'elle modifiera le contenu du buffer point� par le pointeur (acc�s en �criture). Une fonction qui prend un const char* d�clare qu'elle va lire le contenu du buffer sans le modifier (acc�s en lecture seule).

Mis � jour le 19 octobre 2004 Luc Hermitte

<string> et <string.h> sont deux fichiers d'en-t�te totalement diff�rents. Le premier est l'en-t�te standard C++ qui d�finit le type std::string.
Le second est un en-t�te h�rit� du langage C qui d�finit diverses fonctions C de manipulation de cha�nes de caract�res. Il est � noter qu'inclure <string.h> est obsol�te, il convient d'inclure <cstring> � la place.
� ce sujet lire aussi Quelle est la diff�rence entre #include <iostream.h> et #include <iostream> ?.

Mis � jour le 19 octobre 2004 Aurelien.Regat-Barrel

Aucune ! Ces deux fonctions renvoient toutes les deux la longueur de la cha�ne. En fait, length() retourne size(), mais on est libre d'utiliser l'une ou l'autre.
Voir aussi Quelle diff�rence entre string::size() et string::capacity() ?

Mis � jour le 19 octobre 2004 Aurelien.Regat-Barrel

size renvoie le nombre de caract�res contenus dans la cha�ne (par exemple 4 pour "abcd") et capacity la capacit� de stockage de la cha�ne, c'est-�-dire le nombre total de caract�res qu'elle peut stocker sans n�cessiter une r�allocation. capacity est donc toujours au moins �gal � size, et peut �tre plus �lev�, en particulier si vous faites un appel � reserve.

Code c++ : S�lectionner tout
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
#include <string> 
#include <iostream> 
  
int main() 
{ 
    using namespace std; 
  
    string s; // la cha�ne est vide 
    cout << "size = " << s.size() << '\t'  // size = 0  
         << "capacity = " << s.capacity()  // capacity = 15 
         << '\n'; 
  
    // on sait que l'on va faire de nombreuses concat�nations, 
    // alors on r�serve de l'espace pour �viter de multiples allocations 
    s.reserve( 26 ); 
    cout << "size = " << s.size() << '\t'  // size = 0  
         << "capacity = " << s.capacity()  // capacity = 31 
         << '\n'; 
  
    // concat�ner les 26 lettres de l'alphabet 
    for ( char c = 'A'; c <= 'Z'; ++c ) 
    { 
        s += c; 
    } 
  
    cout << "size = " << s.size() << '\t'  // size = 26  
         << "capacity = " << s.capacity()  // capacity = 31 
         << '\n'; 
  
    s = "une assez longue cha�ne qui oblige a faire une allocation"; 
    cout << "size = " << s.size() << '\t'  // size = 57 
         << "capacity = " << s.capacity()  // capacity = 63 
         << '\n'; 
}
La valeur retourn�e par capacity peut varier d'un compilateur � l'autre, ou plut�t d'une impl�mentation de la STL � l'autre.
C'est pourquoi il est fort probable que vous n'obteniez pas les m�mes r�sultats si votre compilateur n'est pas celui utilis� pour ce test (Visual C++ .Net 2003).
Par contre quelque soit votre compilateur les valeurs retourn�es par size devraient �tre les m�me.

Voir aussi Quelle est la diff�rence entre string::length() et string::size() ?

Mis � jour le 19 octobre 2004 Aurelien.Regat-Barrel

c_str() retourne un pointeur sur une cha�ne de caract�res constante termin�e par le caract�re nul (cha�ne de caract�res C). data() retourne aussi un pointeur sur une cha�ne de caract�res constante, mais la pr�sence du caract�re terminal nul n'est pas exig�e donc non garantie. Donc c_str() renvoie un pointeur constant sur un buffer contenant size() + 1 caract�res et data() sur un buffer de size() caract�res.

Mis � jour le 19 octobre 2004 Aurelien.Regat-Barrel

Il ne faut faire aucune hypoth�se quant � la fa�on dont est impl�ment�e la classe string. Le comportement de cette derni�re est sp�cifique � presque chaque version de compilateur C++ existant.
Par exemple, les caract�res peuvent ne pas �tre stock�s en interne de mani�re contigu� (on peut envisager un syst�me de concat�nation rapide via un cha�nage de sous cha�nes de caract�res).
Ou encore, certaines impl�mentations utilisent le Copy On Write (COW) qui implique que plusieurs objets string peuvent en interne partager le m�me espace m�moire pour stocker leurs caract�res.
Le seul point commun � toutes ces impl�mentations est que l'on est assur� que le pointeur retourn� par c_str() ou data() d�signe une cha�ne de caract�res contigus. Mais rien n'emp�che celui-ci de pointer vers une copie cr��e pour l'occasion !
C'est pourquoi il est tr�s important de ne jamais modifier la cha�ne retourn�e par ces fonctions.
Un autre point important est que ce pointeur peut �tre invalid� suite � une modification, et que sa dur�e de vie n'exc�de pas celle de l'objet associ�. Le code suivant illustre ces deux points :

Code c++ : S�lectionner tout
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
#include <string> 
  
int main() 
{ 
    using std::string; 
  
    string str( "Hello" ); 
    const char * c_str = str.c_str(); // ok 
  
    // erreur 1 : invalidation de pointeur suite � une modification 
    str += " World !"; // concat�ner " World !" � "Hello" 
    // maintenant c_str est invalide, et ne doit plus �tre utilis� ! 
  
    c_str = str.c_str(); 
    // erreur 2 : l'utilisation de [] peut aussi invalider c_str 
    char c = str[ 0 ]; // ok, acc�s en lecture seulement 
    str[ 0 ] = 'A'; // modification d'un caract�re 
    // maintenant c_str est invalide, et ne doit plus �tre utilis� ! 
  
    // erreur 3 : invalidation de pointeur suite � une destruction 
    { 
        // variable temporaire � ce bloc 
        string str2( "Temporaire" ); 
        c_str = str2.c_str(); // ok 
    } // fin du bloc : str2 est d�truite 
    // maintenant c_str est invalide car la cha�ne point�e a �t� d�truite !     
}
Le code ci-dessus compile parfaitement, mais provoque un certain nombre d'erreurs d'ex�cution qui varie en fonction de l'impl�mentation de string utilis�e.

Mis � jour le 19 octobre 2004 Aurelien.Regat-Barrel

string (mais aussi <algorithm>) poss�de deux fonctions de recherche qui toutes les deux recherchent la premi�re occurrence d'un �l�ment :

Code c++ : S�lectionner tout
1
2
3
4
5
string s = "abcdef"; 
if ( s.find( 'c' ) == s.find_first_of( 'c' ) ) 
{ 
    // ce test est vrai 
}
La diff�rence entre les deux est que find recherche la premi�re occurrence d'un caract�re ou d'une cha�ne de caract�res dans une string tandis que find_first_of recherche le premier caract�re de la cha�ne qui soit �gal � l'un de ceux donn�s en param�tre.
Donc dans le cas de la recherche d'un caract�re il n'y a pas de diff�rence entre les deux, mais ces deux fonctions sont tr�s diff�rentes si leur argument est une cha�ne de caract�res. find consid�rera cette cha�ne comme une sous cha�ne � rechercher, et find_first_of comme une liste de caract�res � rechercher.

Code c++ : S�lectionner tout
1
2
3
4
string s = "abcba"; 
  
cout << s.find( "ba" ) << '\n'; // affiche 3 
cout << s.find_first_of( "ba" ) << '\n'; // affiche 0
L'appel � find retourne la position de la sous cha�ne � ba � dans "abcba" (3� position).
L'appel � find_first_of renvoie la position de la premi�re occurrence de n'importe lequel des caract�res pass�s en param�tre, c'est-�-dire ici 0 (premi�re lettre de "abcba" = a qui figure bien dans la liste "ba").

Mis � jour le 19 octobre 2004 Aurelien.Regat-Barrel

Il suffit de tester le r�sultat de l'op�ration de conversion, comme le fait la fonction g�n�rique from_string de la question Comment convertir une string en un objet de n'importe quel type ?. Ce principe est expliqu� dans Comment fonctionne le test de r�ussite de conversion if ( str >> num ) ?

Code c++ : S�lectionner tout
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
#include <sstream>   
  
bool is_float( const std::string & Str ) 
{ 
    // cr�er un flux � partir de la cha�ne donn�e 
    std::istringstream iss( Str ); 
    // cr�er un objet temporaire pour la conversion 
    float tmp; 
    // tenter la conversion et 
    // v�rifier qu'il ne reste plus rien dans la cha�ne 
    return ( iss >> tmp ) && ( iss.eof() ); 
} 
  
int main() 
{ 
    is_float( "10.0" ); // vrai 
    is_float( "abcd" ); // faux 
    is_float( "10.0abcd" ); // faux gr�ce au 2� test 
}
Apr�s avoir converti avec succ�s Str en un float, on tente d'extraire une cha�ne, op�ration qui ne peut �chouer que s'il ne reste plus rien une fois le float extrait. Cela permet de faire �chouer le troisi�me test avec "10.0abcd.
Cette solution sp�cifique aux float peut ais�ment �tre g�n�ralis�e gr�ce aux templates :

Code c++ : S�lectionner tout
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
#include <sstream>   
  
template<typename T> 
bool is_of_type( const std::string & Str ) 
{ 
    // cr�er un flux � partir de la cha�ne donn�e 
    std::istringstream iss( Str ); 
    // cr�er un objet temporaire pour la conversion 
    T tmp; 
    // tenter la conversion et 
    // v�rifier qu'il ne reste plus rien dans la cha�ne 
    return ( iss >> tmp ) && ( iss.eof() ); 
} 
  
int main() 
{ 
    is_of_type<float>( "10.5" ); // vrai 
    is_of_type<int>( "10.5" ); // faux gr�ce au 2� test 
}
L'utilisation des templates n�cessite ici leur instanciation explicite, c'est-�-dire de sp�cifier au moment de l'utilisation de la fonction le type dont on souhaite v�rifier la conversion depuis une string. Comme le montre cet exemple, la r�ussite ou non de la conversion est d�termin�e par le comportement de l'op�rateur >> pour le type donn�. La fonction is_of_type devrait donc plut�t s'appeler is_convertible_in_type. Pour tester avec plus de rigueur le contenu d'une string il faut donc se tourner vers une autre solution, comme l'utilisation d'expressions r�guli�res.

Mis � jour le 18 avril 2005 Aurelien.Regat-Barrel LFE

Le type standard pour manipuler des cha�nes en C++ est std::string. Mais si l'on regarde de plus pr�s, on s'aper�oit qu'il ne s'agit en fait que qu'un typedef :

Code c++ : S�lectionner tout
1
2
3
4
namespace std 
{ 
    typedef basic_string<char, char_traits<char>, allocator<char> > string; 
}
Le premier param�tre repr�sente le type des caract�res manipul�s, le troisi�me est l'allocateur et nous importe peu ici. Ce qui est int�ressant, c'est le second param�tre qui d�finit les op�rations de base (recherches, comparaisons.) sur le type manipul�. Ainsi, pour cr�er des cha�nes de caract�res ne tenant pas compte de la casse (diff�rence entre majuscules et minuscules) il suffit de cr�er un char_traits perso :

Code c++ : S�lectionner tout
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
struct ci_char_traits : public std::char_traits<char> 
// on d�rive du char_traits par d�faut, ainsi on h�rite des fonctions que nous ne voulons pas red�finir 
{ 
    static bool eq(char c1, char c2) 
    { 
        return toupper(c1) == toupper(c2); 
    } 
  
    static bool ne(char c1, char c2) 
    { 
        return toupper(c1) != toupper(c2); 
    } 
  
    static bool lt(char c1, char c2) 
    { 
        return toupper(c1) < toupper(c2); 
    } 
  
    static int compare(const char* s1, const char* s2, size_t n) 
    { 
        return memicmp(s1, s2, n); // si disponible sur votre compilateur 
    } 
  
    static const char* find(const char* s, int n, char a) 
    { 
        while ((n-- > 0) && (toupper(*s) != toupper(a))) 
            ++s; 
  
        return s; 
    } 
};
Il ne nous reste plus ensuite qu'� cr�er le basic_string correspondant :

Code c++ : S�lectionner tout
typedef std::basic_string<char, ci_char_traits> ci_string;
L'avantage est que celui-ci se manipule exactement comme un std::string normal :

Code c++ : S�lectionner tout
1
2
3
4
ci_string s1 = "salut"; 
ci_string s2 = "SAluT"; 
  
cout << (s1 == s2); // affiche "1" (vrai)
Pour des informations plus compl�tes, vous pouvez jeter un oil � l'item n�29 des GOTW (Guru Of The Week).

Mis � jour le 17 octobre 2005 Laurent Gomila

Le plus simple est d'utiliser la fonction std::reverse() sur la cha�ne existante, ou d'en cr�er une nouvelle en passant un it�rateur inverse au constructeur de std::string.

Code c++ : S�lectionner tout
1
2
3
4
5
6
7
8
9
10
#include <algorithm> // pour std::reverse() 
#include <string>  
  
std::string chaine = "Bonjour";  
  
// Inversion directe de la cha�ne  
std::reverse(chaine.begin(), chaine.end());  
  
// Autre m�thode : cr�ation d'une cha�ne invers�e  
std::string inverse( chaine.rbegin(), chaine.rend() );

Mis � jour le 18 avril 2005 Laurent Gomila

std::string ne dispose pas de fonction �quivalente � la fonction C standard strtok(). Il existe de nombreuses fa�ons de r�aliser un �quivalent � cette fonction. L'une des solutions les plus simples et de proc�der au d�coupage sur un istringstream au moyen de std::getline() :

Code c++ : S�lectionner tout
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
#include <sstream> 
#include <string> 
#include <iostream> 
  
using namespace std; 
  
int main() 
{ 
    istringstream iss( "mot1;mot2;mot3;mot4" ); 
    string mot; 
    while ( std::getline( iss, mot, ';' ) ) 
    { 
        cout << mot << '\n'; 
    } 
}
Par d�faut getline() sert � extraire des cha�nes d�limit�es par un saut de ligne, mais comme le montre l'exemple pr�c�dent il est possible de sp�cifier un autre s�parateur (ici le caract�re ';').
Attention : getline() va consid�rer tout ce qui se trouve entre deux ';' comme �tant une ligne � extraire. Cela veut dire que la phrase "mot1 mot2;;mot3" (notez le double point virgule entre mot2 et mot3) sera d�coup�e en "mot1 mot2", "" (cha�ne vide) et "mot3". Cette utilisation de getline() ne permet aussi de sp�cifier qu'un seul s�parateur. Si vos mots sont s�par�s par de simples espaces, vous pouvez aussi vous inspirer de [Exemple] Comment manipuler un tableau de string ?.

Pour quelque chose de plus �volu�, vous pouvez vous tourner vers boost::tokenizer (voir Comment d�couper une cha�ne avec boost::tokenizer ?) ou encore r�aliser votre propre fonction de d�coupage en vous inspirant de ceci : Tokenizing.

Mis � jour le 18 avril 2005 Aurelien.Regat-Barrel

On ne peut pas. Le code suivant ne compile pas :

Code c++ : S�lectionner tout
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
// fonctions de traitement 
void parametre_input(); 
void parametre_output(); 
void parametre_inconnu(); 
  
// appel des fonctions de traitement 
void analyse_parametre( const char * Param ) 
{ 
    switch ( Param ) 
    { 
    case "/input": 
        parametre_input(); break; 
  
    case "/output": 
        parametre_output(); break; 
  
    default: 
        parametre_inconnu(); 
    } 
}
Il est possible d'arriver au r�sultat escompt� en cha�nant une s�rie de if testant les diff�rentes cha�nes, mais une solution �l�gante en C++ consiste � utiliser std::map d�fini dans l'en-t�te standard <map>. Une map permet d'associer un �l�ment � une cl�. Dans notre cas nous allons associer une fonction de traitement � une cha�ne de caract�res :

Code c++ : S�lectionner tout
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
// fonctions de traitement 
void parametre_input(); 
void parametre_output(); 
void parametre_inconnu(); 
  
// type pointeur de fonction de traitement 
typedef void (*parametre_fct)(); 
  
void analyse_parametre( const string & Param ) 
{ 
    static map<string, parametre_fct> param_map; 
  
    // initialiser la map si ce n'est pas fait 
    if ( param_map.empty() ) 
    { 
        param_map[ "/input" ] = parametre_input; 
        param_map[ "/output" ] = parametre_output; 
    } 
  
    // rechercher la fonction associ�e � Param 
    map<string, parametre_fct>::const_iterator i = param_map.find( Param ); 
    if ( i == param_map.end() ) 
    { 
        // �chec 
        parametre_inconnu(); 
    } 
    else 
    { 
        // appeler la fonction associ�e 
        (i->second)(); 
    } 
}

Mis � jour le 22 novembre 2004 Aurelien.Regat-Barrel

De la m�me mani�re que les cha�nes ANSI, mais au moyen du type std::wstring qui est d�fini dans le fichier d'en-t�te standard <string>.
Il s'agit d'une sp�cialisation de std::basic_string pour le type wchar_t (caract�re Unicode) au m�me titre que std::string l'est pour le type char.

Code c++ : S�lectionner tout
1
2
3
4
5
6
7
8
9
#include <string> 
#include <iostream> 
  
int main() 
{ 
    std::wstring s = L"Cha�ne unicode"; 
    wchar_t c = s[ 0 ]; // c = L'C' 
    std::wcout << s; 
}
Notez qu'une version Unicode existe aussi pour les flux, afin de les rendre utilisables avec wstring et wchar_t. Ainsi, on utilisera wcout pour l'affichage, wcin pour la saisie, wifstream pour la lecture de fichiers.
Cependant, en ce qui concerne les fichiers, les caract�res wchar_t sont convertis de mani�re transparente en char au moment de l'�criture. Le C++ standard ne permet pas en effet de manipuler des fichiers Unicode.

Pour r�aliser les conversions string <-> wstring, voir Comment effectuer les conversions de texte ASCII <-> Unicode ?.

Mis � jour le 18 avril 2005 Aurelien.Regat-Barrel

Les fonctions suivantes permettent, via l'utilisation de la biblioth�que standard, de transformer un texte Unicode en ASCII (narrow), et vice-versa (widen).

Code c++ : S�lectionner tout
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
#include <string> 
#include <locale> 
#include <vector> 
  
std::string narrow(const std::wstring& ws) 
{ 
    std::vector<char> buffer(ws.size()); 
    std::locale loc("english"); 
    std::use_facet< std::ctype<wchar_t> >(loc).narrow(ws.data(), ws.data() + ws.size(), '?', &buffer[0]); 
  
    return std::string(&buffer[0], buffer.size()); 
} 
  
std::wstring widen(const std::string& s) 
{ 
    std::vector<wchar_t> buffer(s.size()); 
    std::locale loc("english"); 
    std::use_facet< std::ctype<wchar_t> >(loc).widen(s.data(), s.data() + s.size(), &buffer[0]); 
  
    return std::wstring(&buffer[0], buffer.size()); 
}

Mis � jour le 17 mars 2008 superspag

Code c++ : S�lectionner tout
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
#include <string>  
#include <algorithm> // remove(), erase() 
#include <iostream>  
  
// supprime toutes les occurrences du caract�re C donn� 
void SupprimeTousLesCaracteres( std::string & Str, char C ) 
{  
    Str.erase( 
        std::remove( Str.begin(), Str.end(), C ), 
        Str.end() );  
}     
  
// supprime tous les caract�res C situ�s au d�but de Str 
std::string SupprimeLesPremiersCaract�res( const std::string & Str, char C ) 
{  
   return Str.substr( 
       Str.find_first_not_of( C ) );  
}  
  
int main() 
{  
    using namespace std; 
  
    // supprimer les quote entre les mots 
    string s1 = "'mot1' 'mot2' 'mot3' 'mot4'"; 
    SupprimeTousLesCaracteres( s1, '\'' ); 
    cout << s1 << '\n'; // affiche "mot1 mot2 mot3 mot4" 
  
    // enlever les espaces g�nants au d�but de la cha�ne 
    string s2 = "     exemple";  
    cout << SupprimeLesPremiersCaract�res( s2, ' ' ); // affiche "exemple" 
}
Notez que le premier exemple (SupprimeTousLesCaracteres) est un cas typique d'utilisation de l'idiome erase-remove qui consiste � combiner la fonction remove() avec la fonction erase() afin de supprimer les �l�ments r�pondant � un certain crit�re (ici au fait d'�tre �gal au caract�re donn�).

Mis � jour le 18 avril 2005 Laurent Gomila

Code c++ : S�lectionner tout
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
#include <vector> 
#include <sstream> 
#include <iostream> 
#include <iterator> 
  
int main() 
{ 
    using namespace std; 
  
    string str = "mot1 mot2 mot3 mot4 mot5 mot6"; 
  
    vector<string> str_list; // liste de mots 
  
    // remplir la liste de mots 
    istringstream iss( str ); 
    copy( 
        istream_iterator<string>( iss ), 
        istream_iterator<string>(), 
        back_inserter( str_list ) ); 
  
    // afficher la liste de mots sur cout 
    copy( 
        str_list.begin(), 
        str_list.end(), 
        ostream_iterator<string>( cout, "\n" ) ); 
  
    // reconstituer une string � partir de la liste de mots 
    ostringstream oss; 
    copy( 
        str_list.begin(), 
        str_list.end(), 
        ostream_iterator<string>( oss, " " ) ); 
  
    string s = oss.str(); 
    cout << s << '\n'; // "mot1 mot2 mot3 mot4 mot5 mot6" 
}

Mis � jour le 19 octobre 2004 Aurelien.Regat-Barrel

Proposer une nouvelle r�ponse sur la FAQ

Ce n'est pas l'endroit pour poser des questions, allez plut�t sur le forum de la rubrique pour �a


R�ponse � la question

Liens sous la question
pr�c�dent sommaire suivant
 

Les sources pr�sent�es sur cette page sont libres de droits et vous pouvez les utiliser � votre convenance. Par contre, la page de pr�sentation constitue une �uvre intellectuelle prot�g�e par les droits d'auteur. Copyright � 2025 Developpez Developpez LLC. Tous droits r�serv�s Developpez LLC. Aucune reproduction, m�me partielle, ne peut �tre faite de ce site et de l'ensemble de son contenu : textes, documents et images sans l'autorisation expresse de Developpez LLC. Sinon vous encourez selon la loi jusqu'� trois ans de prison et jusqu'� 300 000 � de dommages et int�r�ts.