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 :

#ifdef dans une macro


Sujet :

C++

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    cedrix57
    Invité(e)
    Par défaut #ifdef dans une macro
    Bonjour,

    Je cherche à faire une macro ou fonction inline de ce genre:


    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    inline CString readID(int id){
      CString strFilter;
      strFilter.LoadString(id);
      return strFilter;
    }
     
    #define transT2(str) \
    #ifdef str \
      readID(id) \
    #else \
      _T("str")
    L'idée est que:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    #define CHAINE "toto"
    CString s1 = transT2(CHAINE); //renvoie "toto"
    CString s2 = transT2(CHAINE_NON_DEFINIE); //renvoie "CHAINE_NON_DEFINIE"
    Quelqu'un sait comment je pourrai faire ce genre de macro?
    Idéalement je voudrais faire ça:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    #define TOTO "toto_modifie1"
    #define TO_TO "toto_modifie2"
    CString s1 = transT2("toto"); //renvoie "toto_modifie1" car TOTO est définie
    CString s1 = transT2("to to"); //renvoie "toto_modifie2" car TO_TO est définie
    CString s1 = transT2("toyota"); //renvoie "toyota" car la macro TOYOTA n'est pas définie
    Je sait pas si c'est possible?

    Merci d'avance

  2. #2
    Rédacteur/Modérateur


    Homme Profil pro
    Network game programmer
    Inscrit en
    Juin 2010
    Messages
    7 147
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 38
    Localisation : Canada

    Informations professionnelles :
    Activité : Network game programmer

    Informations forums :
    Inscription : Juin 2010
    Messages : 7 147
    Billets dans le blog
    4
    Par défaut
    Bonjour,

    c'est impossible.
    Il te faut revoir ce qu'est réellement une macro, ça sert juste à effectuer un remplacement avant la compilation.
    La passe n'est réalisée qu'une seule fois.
    Le contenu des chaînes de caractères ne sera jamais modifié.
    C'est sensible à la casse.

    Ton besoin est surement mal définie, les mécanismes que tu espères mettre en place ne sont pas clairs et bancals.

    Par exemple
    - pourquoi des define et non des enum ?
    - pourquoi une macro et non une fonction ?
    Pensez à consulter la FAQ ou les cours et tutoriels de la section C++.
    Un peu de programmation réseau ?
    Aucune aide via MP ne sera dispensée. Merci d'utiliser les forums prévus à cet effet.

  3. #3
    Membre actif
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Décembre 2011
    Messages
    54
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : Service public

    Informations forums :
    Inscription : Décembre 2011
    Messages : 54
    Par défaut
    Bonjour,

    Alors, plusieurs choses:
    - un ifdef dans une définition de macro n'est pas une syntaxe valide. Donc tu ne pourras pas utiliser ça
    - ceci mis à part, dans le code de ta macro, d'où sort "id"? Et du coup, dans tes exemples, lorsque le symbole est défini, la macro devrait plutôt retourner une chaine contenant un entier
    - _T("str") fera que si le symbole n'est pas défini, tu auras toujours "str" dans ta chaine de caractère au final. Pour transformer un symbole en chaine de caractère, ça se fait en utilisant le caractère # devant ton symbole. ça donnerait _T(#str). Mais le problème c'est que ta chaine de caractère vaudra toujours "str" quand même, puisque c'est ce symbole qui sera transformé.

    Bref, il y a pas mal d'incompréhension sur le langage et la syntaxe j'ai l'impression. Quelle est la finalité? J'imagine que c'est pour gérer la localisation d'une application?

  4. #4
    cedrix57
    Invité(e)
    Par défaut
    Bref, il y a pas mal d'incompréhension sur le langage et la syntaxe j'ai l'impression.
    Oui je me doutais que cela n'était probablement pas possible...mais pour illustrer mon idée j'ai pas trouvé mieux que de mettre du code faux.

    Quelle est la finalité? J'imagine que c'est pour gérer la localisation d'une application?
    En fait je développe avec Microsoft Visual C++ et les MFC. Dans mon programme j'ai plusieurs chaîne de caractère. Je vais devoir internationaliser mon programme dans plusieurs langue. Pour ceux qui connaissent la programmation C++ MFC, il existe un système de ressource dans lesquelles on peut définir ce qu'on appelle un "table string". Dans ce type de ressource il est possible de définir plusieurs chaîne de caractère et d'associer à chacune un ID. Ensuite le chargement d'une chaîne se fait de la manière suivante:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    CString strFilter;
    strFilter.LoadString(id);
    Mais j'aime pas trop ce système car à chaque fois que je déclare une chaîne je dois aller dans l'éditeur de ressource (qui bien-sûr ne marche que si je charge deux fois un même projet et utilise la deuxième instance), et la définir ce qui est long à faire et me fait perdre mon fil.

    Tu coup j'aimerai bien avoir une fonction/macro où n'importe qui fasse un truc du genre:
    Si l'ID est définie (ça veut dire que j'ai pris le temps d'aller éditer mon fichier ressource, ce que je peux éventuellement automatiser avec un script python) j'aimerai bien le charger la chaîne depuis le fichier ressource.
    Sinon je renvoie une chaîne de caractères.

    Pour le moment j'ai pensé à un seul truc:
    Code : 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
     
    inline CString readID(int id){
      CString strFilter;
      strFilter.LoadString(id);
      return strFilter;
    }
     
    CString strFilter = 
    #ifdef ID_STRING
    readID(ID_STRING);
    #else
    _T("ID_STRING");
     
    CString strFilter2 = 
    #ifdef ID_STRING2
    readID(ID_STRING2);
    #else
    _T("ID_STRING2");
    Pour chaque chaîne je peux les charger de cette manière...mais mon objectif étant de gagner du temps j'aimerai bien encapsuler ça quelque par mais j'ai pas encore trouver comment faire.

  5. #5
    Rédacteur/Modérateur


    Homme Profil pro
    Network game programmer
    Inscrit en
    Juin 2010
    Messages
    7 147
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 38
    Localisation : Canada

    Informations professionnelles :
    Activité : Network game programmer

    Informations forums :
    Inscription : Juin 2010
    Messages : 7 147
    Billets dans le blog
    4
    Par défaut
    Et à quel moment as-tu lu la doc de LoadString ?

    Qui indique clairement qu'elle renvoit un bool indiquant si oui ou non la chaîne a été trouvée et chargée ?

    L'idée de defines pour les id est mauvaise amha, tu veux un id, tu fous un id, et tu cherches pas s'il existe ou non, ce doit être un id.
    Que la chaîne correspondante existe ou non ne change pas ça.

    Après éventuellement tu traficoteras quelque chose autour.
    Pensez à consulter la FAQ ou les cours et tutoriels de la section C++.
    Un peu de programmation réseau ?
    Aucune aide via MP ne sera dispensée. Merci d'utiliser les forums prévus à cet effet.

  6. #6
    Membre actif
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Décembre 2011
    Messages
    54
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : Service public

    Informations forums :
    Inscription : Décembre 2011
    Messages : 54
    Par défaut
    Personnellement, j'éviterai de coller ça directement dans le code. Je passerai plutôt par une ressource externe, comme par exemple un fichier pour chaque langue.
    Il y a certainement des libs qui gèrent la localisation, mais si je devais en écrire une, je ferais simple, avec une classe CLocalisation par exemple, qui lirait ces différents fichiers de ressource dans lequel une chaine de caractère serait associé à un ID (sous forme d'entier ou de chaine de caractère), chargeant tout ça dans une map. Ensuite, tu l'interroges comme ceci:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    CLocalisation localisation();
    localisation.SetLocal("FR");
    CString strFileNotFound = localisation.GetString("FILE_NOT_FOUND");
    et l'objet s'occupe de te retourner la vrai chaine de caractère si elle est présente dans la map, sinon il te retourne l'ID que tu lui as passé en param.

    Faire tout ça avec une macro implique plus ou moins une partie de code en dur, c'est toujours assez genant. Surtout si tes chaines de caractères sont déclarées avec des define, ça va dire que la moindre modif de texte nécessite une compilation. Au moins, avec un fichier de ressource externe, tu peux même donner un fichier à traduire à quelqu'un, sans rien toucher aux sources.


    My 2 cents.

  7. #7
    Expert éminent

    Femme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Juin 2007
    Messages
    5 202
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Localisation : France, Essonne (Île de France)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels

    Informations forums :
    Inscription : Juin 2007
    Messages : 5 202
    Par défaut
    Tu as regardé du coté de gettext?

Discussions similaires

  1. newline dans une macro procédure
    Par Puyi dans le forum C
    Réponses: 9
    Dernier message: 19/04/2006, 16h01
  2. Exécuter une sub d'un module dans une macro
    Par pnoel-bi dans le forum Access
    Réponses: 3
    Dernier message: 03/03/2006, 10h39
  3. Code asm dans une macro C
    Par progfou dans le forum C
    Réponses: 11
    Dernier message: 01/03/2006, 18h50
  4. Comment insérer une macro excel dans une macro word?
    Par max2245 dans le forum VBA Word
    Réponses: 15
    Dernier message: 07/01/2006, 17h44
  5. pb dans une macro excel VB
    Par syl221 dans le forum Macros et VBA Excel
    Réponses: 6
    Dernier message: 20/10/2005, 17h29

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