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

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

C++ Discussion :

Macro ATL pour conversion de type


Sujet :

C++

  1. #1
    Membre confirmé
    Inscrit en
    Juin 2005
    Messages
    110
    Détails du profil
    Informations forums :
    Inscription : Juin 2005
    Messages : 110
    Par défaut Macro ATL pour conversion de type
    Bonjour à tous,

    Je cherche à convertir proprement un CHAR * en CComBSTR et vice versa de manière propre. J'ai fini par trouver ça:

    http://msdn.microsoft.com/en-us/library/87zae4a3.aspx

    Le problème qui se pose c'est que je ne sais pas si j'ai affaire à de l'ANSI ou de l'UNICODE pour le CComBSTR car d'après le lien qui suit ça peut être soit l'un soit l'autre (avec une préférence pour l'UNICODE):

    http://msdn.microsoft.com/en-us/library/zh7x9w3f.aspx

    J'ai exactement le même genre de question en ce qui concerne le char * . Je sais que c'est du code ASCII, mais comment c'est codé? En ANSI, ou en generic character string?

    Et c'est là que je me perds, si mon CComBSTR est de l'ANSI, et le char * est de l'ANSI aussi, je vais devoir écrire une macro qui converti de l'ANSI en ANSI...

    Quelqu'un peut-il éclairer ma lanterne?

    D'avance merci

  2. #2
    Expert éminent
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 393
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 41
    Localisation : France

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 393
    Par défaut
    Conversion char* en CComBSTR: Utiliser tout simplement le constructeur de CComBSTR à partir de ton const char*.
    Ta chaîne "ANSI" (un terme plus exact est "ASCII étendu", car en fait, les pages de code Windows n'ont jamais été standardisées par l'ANSI) sera automatiquement convertie en CComBSTR Unicode UTF-16, en utilisant la page de codes "ANSI" courante (mais je crois que c'est "courante du système" et non pas "courante du programme").

    Conversion CComBSTR en char* : Plus compliqué. Sur une version récente d'ATL, tu peux utiliser la classe COLE2A.

    Je ne comprends pas ce que tu veux dire par "Generic character string". Tout ce que je sais, c'est qu'un char* est en ASCII étendu. Pratiquement jamais en UTF-8, car les fonctions de Windows ne supporte que la conversion depuis et vers ce format, mais pas la manipulation de chaînes UTF-8.

    Une CComBSTR, ce n'est pas de "l'ANSI", mais de l'Unicode UTF-16. Et ce, depuis que Windows est passé du 16 (Win3.11) au 32 bits.

    PS: Plutôt que des char, tu devrais utiliser des TCHAR quand tu programmes sous Windows (et donc, utiliser COLE2T au lieu de COLE2A).
    SVP, pas de questions techniques par MP. Surtout si je ne vous ai jamais parlé avant.

    "Aw, come on, who would be so stupid as to insert a cast to make an error go away without actually fixing the error?"
    Apparently everyone.
    -- Raymond Chen.
    Traduction obligatoire: "Oh, voyons, qui serait assez stupide pour mettre un cast pour faire disparaitre un message d'erreur sans vraiment corriger l'erreur?" - Apparemment, tout le monde. -- Raymond Chen.

  3. #3
    Membre confirmé
    Inscrit en
    Juin 2005
    Messages
    110
    Détails du profil
    Informations forums :
    Inscription : Juin 2005
    Messages : 110
    Par défaut
    Bonjour Medinoc,

    Pour la conversion de char * en CComBSTR, ça tourne, merci beaucoup, par contre dans l'autre sens je coince. J'ai fait ça:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
     
    #include "atlbase.h"
    #include "atlconv.h"
     
    CComBSTR pbstrBackupXML = L"";
    char * CharXML = NULL;
    CHECK_SUCCESS(pBackupComponent->SaveAsXML(&pbstrBackupXML));
    COLE2A CharXML(pbstrBackupXML);
    J'ai des messages d'erreurs pas sympa du tout:

    error C2065: 'COLE2A'*: identificateur non déclaré
    error C2146: erreur de syntaxe*: absence de ';' avant l'identificateur 'CharXML'
    error C2064: le terme ne correspond pas à une fonction qui prend 1 arguments

    Je me dit que c'est peut-être à cause de ça:
    Header file: AtlBase.h, AtlConv.h (declared in AtlConv.h)

    C'est quoi le "declared in AtlConv.h"? J'ai mal fait mes include?

    Je me suis basé sur le msdn pour ça:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
     
    //Example 1
    // Convert LPCWSTR to LPCSTR.
    void ExampleFunction1(LPCWSTR pszW)
    {
       // Create an instance of CW2A, called pszA,
       // and initialize it with pszW.
       CW2A pszA(pszW);
       // pszA works like an LPCSTR, and can be used thus:
       ExampleFunctionA(pszA);  
       // Note: pszA will become invalid when it goes out of scope.
    }
    PS: "Generic character string" est représenté par le type "T" sur la page dont je parlais dand le premier post. Désolé si je l'ai mal employé :-/

  4. #4
    Expert éminent
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 393
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 41
    Localisation : France

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 393
    Par défaut
    Pour T, j'appelle-ça simplement "une chaîne de TCHAR".

    Pour COLE2A, es-tu sûr que tu n'es pas sous Visual 6 (ou antérieur), au moins ?
    SVP, pas de questions techniques par MP. Surtout si je ne vous ai jamais parlé avant.

    "Aw, come on, who would be so stupid as to insert a cast to make an error go away without actually fixing the error?"
    Apparently everyone.
    -- Raymond Chen.
    Traduction obligatoire: "Oh, voyons, qui serait assez stupide pour mettre un cast pour faire disparaitre un message d'erreur sans vraiment corriger l'erreur?" - Apparemment, tout le monde. -- Raymond Chen.

  5. #5
    Membre Expert
    Avatar de white_tentacle
    Profil pro
    Inscrit en
    Novembre 2008
    Messages
    1 505
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Novembre 2008
    Messages : 1 505
    Par défaut
    salut !

    Pourquoi tu ne passes pas par des _bstr_t ?

  6. #6
    Membre confirmé
    Inscrit en
    Juin 2005
    Messages
    110
    Détails du profil
    Informations forums :
    Inscription : Juin 2005
    Messages : 110
    Par défaut
    Pour le T, d'accord, je retiens.

    En ce qui concerne mon IDE, visual C++ 2008 express.

    Laisse moi deviner. Il y a une limitation parce que je suis sous une version express et que je n'ai pas les bon .h?

  7. #7
    Expert éminent
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 393
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 41
    Localisation : France

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 393
    Par défaut
    Eh bien normalement, sous les versions Express, tu n'as pas ATL du tout.
    Bien que les versions Express de Visual Studio soient gratuites, ATL et MFC restent des bibliothèques payantes.

    Par contre, les _bstr_t doivent toujours être présentes, vu qu'elles font partie d'une autre bibliothèque (le Compiler COM Support).
    SVP, pas de questions techniques par MP. Surtout si je ne vous ai jamais parlé avant.

    "Aw, come on, who would be so stupid as to insert a cast to make an error go away without actually fixing the error?"
    Apparently everyone.
    -- Raymond Chen.
    Traduction obligatoire: "Oh, voyons, qui serait assez stupide pour mettre un cast pour faire disparaitre un message d'erreur sans vraiment corriger l'erreur?" - Apparemment, tout le monde. -- Raymond Chen.

  8. #8
    Membre confirmé
    Inscrit en
    Juin 2005
    Messages
    110
    Détails du profil
    Informations forums :
    Inscription : Juin 2005
    Messages : 110
    Par défaut
    Grumpffff....

    Sinon, j'avais trouvé cette fonction sur ccpfrance.com
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
     
    void BSTRtoASC (BSTR str, char * &strRet)
    {
        if ( str != NULL )
       {
           unsigned long length = WideCharToMultiByte (CP_ACP, 0, str, SysStringLen(str),
                                                NULL, 0, NULL, NULL);
           strRet = new char[length];
            length = WideCharToMultiByte (CP_ACP, 0, str, SysStringLen(str), 
                               reinterpret_cast <char *>(strRet), length, NULL, NULL);
            strRet[length] = '\0';
        }
    }
    C'est propre, ou il vaut mieux faire autrement?

  9. #9
    Expert éminent
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 393
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 41
    Localisation : France

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 393
    Par défaut
    Ça m'a l'air à peu près propre, mais un peu trop C++ pour moi, surtout pour l'allocation par new[].
    Et aussi, je ne sais jamais s'il faut faire new[length] ou new[length+1]...
    SVP, pas de questions techniques par MP. Surtout si je ne vous ai jamais parlé avant.

    "Aw, come on, who would be so stupid as to insert a cast to make an error go away without actually fixing the error?"
    Apparently everyone.
    -- Raymond Chen.
    Traduction obligatoire: "Oh, voyons, qui serait assez stupide pour mettre un cast pour faire disparaitre un message d'erreur sans vraiment corriger l'erreur?" - Apparemment, tout le monde. -- Raymond Chen.

  10. #10
    Membre confirmé
    Inscrit en
    Juin 2005
    Messages
    110
    Détails du profil
    Informations forums :
    Inscription : Juin 2005
    Messages : 110
    Par défaut
    Je l'ai testé sur ecrire ma CComBSTR dans un fichier xml, et ça marche plutot bien, il semble qu'il n'y ai pas d'erreur. C'est juste que je trouvais l'écriture des Macro plus "lisible".

    Encore merci

  11. #11
    Expert éminent
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 393
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 41
    Localisation : France

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 393
    Par défaut
    Ce que j'ai du mal à comprendre, c'est comment tu peux avoir une CComBSTR si tu n'as droit ni à ATL ni à MFC...

    PS: Si tu utilises la fonction ci-dessus, ne pas oublier le delete[]...
    SVP, pas de questions techniques par MP. Surtout si je ne vous ai jamais parlé avant.

    "Aw, come on, who would be so stupid as to insert a cast to make an error go away without actually fixing the error?"
    Apparently everyone.
    -- Raymond Chen.
    Traduction obligatoire: "Oh, voyons, qui serait assez stupide pour mettre un cast pour faire disparaitre un message d'erreur sans vraiment corriger l'erreur?" - Apparemment, tout le monde. -- Raymond Chen.

  12. #12
    Membre confirmé
    Inscrit en
    Juin 2005
    Messages
    110
    Détails du profil
    Informations forums :
    Inscription : Juin 2005
    Messages : 110
    Par défaut
    ça, je ne saurais pas te dire, mais j'ai un atlbase.h sur mon système, suite à l'install du sdk.

  13. #13
    Expert éminent
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 393
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 41
    Localisation : France

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 393
    Par défaut
    Eh bien, si tu possède un atlconv.h, COLE2A devrait marcher.
    Rajoute peut-être un using namespace ATL; après tes inclusions...
    SVP, pas de questions techniques par MP. Surtout si je ne vous ai jamais parlé avant.

    "Aw, come on, who would be so stupid as to insert a cast to make an error go away without actually fixing the error?"
    Apparently everyone.
    -- Raymond Chen.
    Traduction obligatoire: "Oh, voyons, qui serait assez stupide pour mettre un cast pour faire disparaitre un message d'erreur sans vraiment corriger l'erreur?" - Apparemment, tout le monde. -- Raymond Chen.

  14. #14
    Membre confirmé
    Inscrit en
    Juin 2005
    Messages
    110
    Détails du profil
    Informations forums :
    Inscription : Juin 2005
    Messages : 110
    Par défaut
    ça ne fonctionne pas non plus, j'ai toujours les même erreurs. J'ai plusieurs atlconv.h sur mon système, installé par le WINDDK. Et si ce n'était pas les bon?

  15. #15
    Expert éminent
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 393
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 41
    Localisation : France

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 393
    Par défaut
    Apparemment, il y a une erreur dans la doc, et COLE2A n'existe pas vraiment (COLE2T existe, par contre). Tu peux utiliser CW2A à la place...
    SVP, pas de questions techniques par MP. Surtout si je ne vous ai jamais parlé avant.

    "Aw, come on, who would be so stupid as to insert a cast to make an error go away without actually fixing the error?"
    Apparently everyone.
    -- Raymond Chen.
    Traduction obligatoire: "Oh, voyons, qui serait assez stupide pour mettre un cast pour faire disparaitre un message d'erreur sans vraiment corriger l'erreur?" - Apparemment, tout le monde. -- Raymond Chen.

  16. #16
    Membre confirmé
    Inscrit en
    Juin 2005
    Messages
    110
    Détails du profil
    Informations forums :
    Inscription : Juin 2005
    Messages : 110
    Par défaut
    J'ai même essayer COLE2T pour voir, toujours la même chose identificateur non déclaré...

    ça se déclare peut-être autrement?

  17. #17
    Expert éminent
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 393
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 41
    Localisation : France

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 393
    Par défaut
    Ceci compile chez moi (un Visual Pro) :
    Code C++ : Sélectionner tout - Visualiser dans une fenêtre à part
    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 <atlbase.h>
    #include <atlconv.h>
    using namespace ATL;
     
    static void FonctionTchar(LPCTSTR scz)
    {
    	//Ne rien faire.
    	(void)scz;
    }
     
    static void FonctionChar(const char * scz)
    {
    	//Ne rien faire.
    	(void)scz;
    }
     
    void TestAtlConv(void)
    {
    	BSTR bs = SysAllocString(L"Toto");
    	if(bs != NULL)
    	{
    		{
    			COLE2T sz(bs);
    			FonctionTchar(sz);
    		}
     
    		{
    			CW2A szA(bs);		
    			FonctionChar(szA);
    		}
     
    		SysFreeString(bs);
    	}
    }
    SVP, pas de questions techniques par MP. Surtout si je ne vous ai jamais parlé avant.

    "Aw, come on, who would be so stupid as to insert a cast to make an error go away without actually fixing the error?"
    Apparently everyone.
    -- Raymond Chen.
    Traduction obligatoire: "Oh, voyons, qui serait assez stupide pour mettre un cast pour faire disparaitre un message d'erreur sans vraiment corriger l'erreur?" - Apparemment, tout le monde. -- Raymond Chen.

  18. #18
    Membre Expert
    Avatar de white_tentacle
    Profil pro
    Inscrit en
    Novembre 2008
    Messages
    1 505
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Novembre 2008
    Messages : 1 505
    Par défaut
    je répète ce que j'ai dit plus haut, pourquoi n'utilises tu pas les _bstr_t ?

    C'est exactement fait pour, ça fait :

    - la copie des char* en BSTR (qui ne sont que des wchar_t* alloués dans un espace mémoire particulier)
    - les conversions ansi-unicode

    tu dois pouvoir écrire simplement :

    puis, ensuite :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
     
    static_cast<const char*>(bs)
    static_cast<const wchar_t*>(bs)
    http://msdn.microsoft.com/en-us/libr...d6(VS.71).aspx

  19. #19
    Membre confirmé
    Inscrit en
    Juin 2005
    Messages
    110
    Détails du profil
    Informations forums :
    Inscription : Juin 2005
    Messages : 110
    Par défaut
    Ah non, chez moi ça ne compile pas, faudra que l'administration m'offre la version pro....

  20. #20
    Expert éminent
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 393
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 41
    Localisation : France

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 393
    Par défaut
    En effet, _bstr_t semble tout à fait approprié.
    SVP, pas de questions techniques par MP. Surtout si je ne vous ai jamais parlé avant.

    "Aw, come on, who would be so stupid as to insert a cast to make an error go away without actually fixing the error?"
    Apparently everyone.
    -- Raymond Chen.
    Traduction obligatoire: "Oh, voyons, qui serait assez stupide pour mettre un cast pour faire disparaitre un message d'erreur sans vraiment corriger l'erreur?" - Apparemment, tout le monde. -- Raymond Chen.

Discussions similaires

  1. Besoin d'aide pour conversion de type
    Par RomyNet dans le forum C#
    Réponses: 6
    Dernier message: 13/08/2012, 12h21
  2. API pour Conversion de données de type comp-3(Cobol)
    Par Kirou dans le forum API standards et tierces
    Réponses: 2
    Dernier message: 01/05/2012, 19h35
  3. Conversion de types pour "insert into"
    Par forumcpp_nono dans le forum JDBC
    Réponses: 0
    Dernier message: 03/09/2009, 09h40
  4. Réponses: 8
    Dernier message: 10/02/2007, 02h44
  5. Réponses: 5
    Dernier message: 18/07/2006, 12h10

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo