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 :

Probleme avec const char*


Sujet :

C

  1. #1
    Membre du Club
    Profil pro
    Inscrit en
    Janvier 2011
    Messages
    74
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Janvier 2011
    Messages : 74
    Points : 46
    Points
    46
    Par défaut Probleme avec const char*
    Bonjour,
    J'ai une librairie avec la fonction suivante:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
     
    int init ( const char *  	ip,
    	    const char *  	mask,
    	    const char *  	gateway 
    	) 		[static]
    Je voudrais lire quatre chaine dans un fichier puis concaténer le tout et envoyer dans init.
    D'abord la partie écriture dans un fichier txt:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    fichier = fopen("test.txt", "w");
    fprintf(fichier, "%s.%s.%s.%s","192","168","1","17");
    fclose(fichier);
    ensuite la lecture et l'appel init:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
     
        char ip[20];
        fp = fopen("/local/out.txt", "w");  // Open "out.txt" on the local file system for writing
        fscanf(fp, "%s",ip);
        fclose(fp);
        EthernetInterface eth;
        eth.init(ip,"255.255.255.0","192.168.1.1");
        pc.baud(115200);
        pc.printf(ip);
        pc.printf("\nBonjour World V1.27!\n\r");
    Déjà le printf(ip) n'affiche rien, et ensuite l'init avec ip ne marche pas car je ne peux pas "pinguer" la carte (LPC1768).
    Il manque peut-etre une fin de chaine? Mais je patauge un peu là.

    Merci

  2. #2
    Expert confirmé
    Inscrit en
    Mars 2005
    Messages
    1 431
    Détails du profil
    Informations forums :
    Inscription : Mars 2005
    Messages : 1 431
    Points : 4 182
    Points
    4 182
    Par défaut
    Ce n'est pas du C. Que vaut ip ?

  3. #3
    Membre du Club
    Profil pro
    Inscrit en
    Janvier 2011
    Messages
    74
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Janvier 2011
    Messages : 74
    Points : 46
    Points
    46
    Par défaut
    J'ai rajouté le bout de code qui manquait, désolé.

  4. #4
    Expert éminent
    Homme Profil pro
    Ingénieur développement matériel électronique
    Inscrit en
    Décembre 2015
    Messages
    1 565
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 61
    Localisation : France, Bouches du Rhône (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Ingénieur développement matériel électronique
    Secteur : High Tech - Électronique et micro-électronique

    Informations forums :
    Inscription : Décembre 2015
    Messages : 1 565
    Points : 7 648
    Points
    7 648
    Par défaut
    Bonjour,
    ligne 3, tu créé un fichier vide,
    ligne 4, tu lis dans ce même fichier ip[], cela ne m'étonne pas beaucoup qu'il ne soit pas affiché.

  5. #5
    Membre du Club
    Profil pro
    Inscrit en
    Janvier 2011
    Messages
    74
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Janvier 2011
    Messages : 74
    Points : 46
    Points
    46
    Par défaut
    Effectivement j'ai corrigé, et cela lit bien ip dans le fichier, par contre l'init de marche pas.
    En fait faut envoyé un (cont char*) et j'envoie un char[20], mais je ne pense pas qu'un zero terminal soit ajouté à ip.
    Comment faire cela, sachant que ip n'aura pas toujours la même longueur (ex "192.168.1.17", et "192.168.1.150" ...etc).
    Merci d'avance

  6. #6
    Modérateur

    Avatar de Bktero
    Homme Profil pro
    Développeur en systèmes embarqués
    Inscrit en
    Juin 2009
    Messages
    4 481
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 36
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : Développeur en systèmes embarqués

    Informations forums :
    Inscription : Juin 2009
    Messages : 4 481
    Points : 13 679
    Points
    13 679
    Billets dans le blog
    1
    Par défaut
    Initialiser le tableau règle le problème ici : char ip[20] = {0};

    Ton ressemble à du C++ avec l'utilisation de méthodes et pourtant tu utilises des fonctions typiques du C plutôt que les fonctions plus classiques du C++. C'est voulu ?

  7. #7
    Membre du Club
    Profil pro
    Inscrit en
    Janvier 2011
    Messages
    74
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Janvier 2011
    Messages : 74
    Points : 46
    Points
    46
    Par défaut
    A vrai dire mon langage "naturel" c'est le pascal objet (Delphi), j'utilise le C/C++ uniquement pour programmer des cartes à microprocesseur. Alors du coup je fais un affreux mélange de C et de C++. Sinon, merci pour la solution.

    Michel

  8. #8
    Expert éminent sénior
    Avatar de Sve@r
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Février 2006
    Messages
    12 689
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Oise (Picardie)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : Aéronautique - Marine - Espace - Armement

    Informations forums :
    Inscription : Février 2006
    Messages : 12 689
    Points : 30 983
    Points
    30 983
    Billets dans le blog
    1
    Par défaut
    Bonjour
    Citation Envoyé par michastro Voir le message
    D'abord la partie écriture dans un fichier txt:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    fichier = fopen("test.txt", "w");
    fprintf(fichier, "%s.%s.%s.%s","192","168","1","17");
    fclose(fichier);
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    fichier = fopen("test.txt", "w");
    fputs("192.168.1.17", fichier);
    fclose(fichier);
    Citation Envoyé par michastro Voir le message
    ensuite la lecture et l'appel init:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
        char ip[20];
        fp = fopen("/local/out.txt", "w");  // Open "out.txt" on the local file system for writing
        fscanf(fp, "%s",ip);
        fclose(fp);
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
        char ip[20];
        fp = fopen("/local/out.txt", "r");  // Open "out.txt" on the local file system for reading (ben oui, quand on veut lire on n'ouvre pas pour "writing" ; ou alors on évite les commentaires en anglais qu'on ne comprend pas...)
        fgets(ip, 20, fp);
        fclose(fp);
    Citation Envoyé par michastro Voir le message
    En fait faut envoyé un (cont char*) et j'envoie un char[20],
    Aucune importance, il y aura cast implicite. Ton char[20] sera stocké, dans la fonction, dans un const char*.

    Citation Envoyé par michastro Voir le message
    mais je ne pense pas qu'un zero terminal soit ajouté à ip.
    Aucun rapport entre "char*", "const char*" et "zéro terminal".
    Un char* ou const char* est un pointeur destiné à stocker une adresse qui sera ensuite considérée comme l'adresse d'une variable char. Un zéro terminal est une valeur spéciale positionnée dans un tableau de char et reconnue par les fonctions de manipulation de chaines lorsqu'elles balayent le tableau.

    Si j'écris char xxx[]={'1', '2', '3'}; init(xxx), ta fonction init stockera ce tableau (l'adresse de son premier élément) dans un "const char*" sans souci même s'il n'y a pas de zéro terminal. Bien entendu ensuite tu n'auras pas le droit d'utiliser des fonctions de lecture de chaine (strlen, printf, strcpy, etc).
    Ceci dit, les fonctions de création de chaines (scanf, fscanf, fgets, etc) rajoutent le zéro terminal (sauf strncpy quand le paramètre "n" est atteint)
    Mon Tutoriel sur la programmation «Python»
    Mon Tutoriel sur la programmation «Shell»
    Sinon il y en a pleins d'autres. N'oubliez pas non plus les différentes faq disponibles sur ce site
    Et on poste ses codes entre balises [code] et [/code]

  9. #9
    Membre du Club
    Profil pro
    Inscrit en
    Janvier 2011
    Messages
    74
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Janvier 2011
    Messages : 74
    Points : 46
    Points
    46
    Par défaut
    Citation Envoyé par Sve@r Voir le message
    Bonjour

    Si j'écris char xxx[]={'1', '2', '3'}; init(xxx), ta fonction init stockera ce tableau (l'adresse de son premier élément) dans un "const char*" sans souci même s'il n'y a pas de zéro terminal. Bien entendu ensuite tu n'auras pas le droit d'utiliser des fonctions de lecture de chaine (strlen, printf, strcpy, etc).
    Ceci dit, les fonctions de création de chaines (scanf, fscanf, fgets, etc) rajoutent le zéro terminal (sauf strncpy quand le paramètre "n" est atteint)
    En écrivant char xxx[]={'1', '2', '3'}; init(xxx), je comprends que init récupère l'adresse de xxx, mais comment la fonction sait qu'il faut traité "123", ou "12", ou "1", ou "123.....", s'il n'y a pas une marque de fin de chaine?

    Merci

  10. #10
    Expert confirmé
    Inscrit en
    Mars 2005
    Messages
    1 431
    Détails du profil
    Informations forums :
    Inscription : Mars 2005
    Messages : 1 431
    Points : 4 182
    Points
    4 182
    Par défaut
    Sans paramètre supplémentaire et sans caractère nul, il n'y a aucun moyen de déterminer la taille de la chaîne effectivement.

  11. #11
    Expert éminent sénior
    Avatar de Sve@r
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Février 2006
    Messages
    12 689
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Oise (Picardie)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : Aéronautique - Marine - Espace - Armement

    Informations forums :
    Inscription : Février 2006
    Messages : 12 689
    Points : 30 983
    Points
    30 983
    Billets dans le blog
    1
    Par défaut
    Citation Envoyé par michastro Voir le message
    En écrivant char xxx[]={'1', '2', '3'}; init(xxx), je comprends que init récupère l'adresse de xxx, mais comment la fonction sait qu'il faut traité "123", ou "12", ou "1", ou "123.....", s'il n'y a pas une marque de fin de chaine?
    Elle ne peut pas. C'est pour ça que j'ai écrit ensuite qu'il était interdit de passer cette adresse à des fonctions de manipulations de chaines (strlen, strcpy, printf). Parce que ces fonctions cherchent un '\0' qui n'y est pas (pas forcément). Et (de façon plus prosaïque) parce que fondamentalement, un tableau de caractères qui n'a pas de '\0' n'est pas une chaine.

    Il est dangereux d'associer "chaines" et "tableaux" parce que ce n'est pas toujours vrai. Une chaine c'est un tableau de caractères qui contient impérativement un caractère '\0'. Donc toute chaine est forcément un tableau de caractères mais tout tableau de caractères n'est pas forcément une chaine. Si '\0' alors chaine, si pas '\0' alors pas chaine. C'est l'axiome de base. Mais cet axiome est tellement fondamental que ça t'autorise ensuite à placer de façon volontairement artificielle un '\0' dans un tableau de caractères et à baptiser (et traiter) ensuite ce tableau comme une vraie chaine (d'ailleurs fondamentalement il l'est !!!). Il m'est d'ailleurs souvent arrivé de convertir des flux de caractères lus depuis un périphérique en chaine (je connaissais le nombre "nb" de caractères lus, me suffisait d'écrire buffer[nb]='\0'). De même celui qui veut "vider" une chaine "xxx" n'aura besoin que d'écrire xxx[0]='\0'. Pourquoi en effet écrire autre chose si toute fonction destinée à traiter "xxx" s'arrêtera au premier '\0' ? => strlen(xxx) renverra "0" même si la suite xxx[1] contient quoi que ce soit (ce qui est, d'ailleurs, impossible à éviter).

    En fait, je n'ai donné cet exemple que pour te faire comprendre que ta fonction peut accepter toute adresse de char même si cette adresse ne pointe pas vers une chaine. Et (de façon plus générale) pour te faire comprendre que le concept "chaine" n'existe pas en C. Le concept existe entre les développeurs C (qui sont humains et qui s'appuient sur des conventions communes) mais le langage lui-même ne sait même pas ce qu'est une chaine.
    Mon Tutoriel sur la programmation «Python»
    Mon Tutoriel sur la programmation «Shell»
    Sinon il y en a pleins d'autres. N'oubliez pas non plus les différentes faq disponibles sur ce site
    Et on poste ses codes entre balises [code] et [/code]

Discussions similaires

  1. probleme avec les char
    Par PastorTroy dans le forum Débuter
    Réponses: 5
    Dernier message: 12/01/2009, 18h46
  2. Petit probleme avec un char*
    Par Nebulis dans le forum C++
    Réponses: 5
    Dernier message: 19/12/2008, 18h58
  3. probleme avec variable char
    Par SimpleMe dans le forum C++
    Réponses: 3
    Dernier message: 02/07/2007, 14h17
  4. Probleme avec les char
    Par king67 dans le forum C
    Réponses: 11
    Dernier message: 10/11/2006, 23h15
  5. problème avec const char * et #define macro
    Par CodeurNé dans le forum C
    Réponses: 5
    Dernier message: 20/09/2006, 21h25

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