cs_Vylco
Messages postés14Date d'inscriptionjeudi 20 septembre 2007StatutMembreDernière intervention26 novembre 2009
-
10 nov. 2009 à 18:00
cs_Vylco
Messages postés14Date d'inscriptionjeudi 20 septembre 2007StatutMembreDernière intervention26 novembre 2009
-
13 nov. 2009 à 17:52
Bonjour, voila j'ai un exo a faire en algo mais je vois pas comment le faire.
la consigne: soit une chaine de caractère. Ecrivez une fonction qui recoit cette chaine et qui extrait toutes les valeures numeriques comprises entre 10 et 30 pour les mettre dans un tableau.
exemple: Ch=<<fsdfs18seryrtr21htrr13rgerger1225rte17htyyt29jy>>
le tableau contiendra : 18,21,13,29
j'ai commencé le début mais je vois pas quelle fonction utilisé et comment savoir une valeure de la chaine des numériques ou non, bref chui perdu , quelqu'un a une idée ? thank you bien d'avance.
cptpingu
Messages postés3837Date d'inscriptiondimanche 12 décembre 2004StatutModérateurDernière intervention28 mars 2023124 12 nov. 2009 à 23:59
Tu n'étais franchement pas loin. Il ne fallait pas de boucle autour de strncpy, puisqu'il copiait déjà tout.
Il te manque quelques truc à reinitialiser, comme chtemp.
On utiliser memset pour affecter une même valeurs à des cases données, et non chtemp = "";
Ca devrait donner ceci (le code n'est pas super propre, il est juste là pour te corriger ton travail actuel, et peut être amélioré):
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <ctype.h>
/*
** Lira tout jusqu'à atteindre un 0.
** Attention, s'il n'y a pas de 0, il peut y avoir débordement !
*/
void display_tab(int* tab)
{
while (tab && *tab)
{
printf("%i ", *tab);
++tab;
}
printf("\n");
}
void Extraire_Num(char *une_chaine)
{
int i = 0;
int mdeb = 0;
int mfin = 0;
int j = 0;
int tab[256] = {0};
char chtemp[256] = {0};
int size = strlen(une_chaine);
int tmp = 0;
for (i = 0; i < size; ++i)
{
if (isdigit(une_chaine[i]))
{
mdeb = i;
i++;
printf("indice de debut %d \n",i);
while (mdeb < size && isdigit(une_chaine[i]))
{
mfin = i;
i++;
}
printf("indice de fin %d\n",i);
memset(chtemp, 0, 256); /* On met 0 dans toutes les 256 cases */
strncpy(chtemp, une_chaine + mdeb, mfin - mdeb + 1);
printf("%s\n", chtemp);
tmp = atoi(chtemp);
if (tmp > 10 && tmp < 30)
{
tab[j] = tmp;
j++;
}
}
}
display_tab(tab);
}
int main(void)
{
char ch[256] = "fsdfs18seryrtr21htrr13rgerger1225rte17htyyt29jy";
/* printf("saisir une chaine alphanumerique\n"); */
/* scanf("%s",ch); */
Extraire_Num(ch);
return 0;
}
cptpingu
Messages postés3837Date d'inscriptiondimanche 12 décembre 2004StatutModérateurDernière intervention28 mars 2023124 10 nov. 2009 à 20:51
Je vais te donner tout ce qu'il faut pour résoudre cet exercice:
Tout d'abord la méthode:
- Tu parcours ta chaînes jusqu'à trouver un chiffre.
- Quand tu en trouves un, tu poses un marqueur (c'est à dire tu retiens la position du caractère dans la chaîne).
- Tu continues de parcourir la chaîne, jusqu'à tomber sur un caractère qui n'est pas un chiffre ou la fin de la chaîne. Tu retiens cette position.
- Tu recopie la chaîne de la première position, à la deuxième (du 1er marqueur jusqu'au deuxième).
- Tu convertis la chaîne obtenu en chiffre.
- Si le chiffre est compris entre 10 et 30, tu l'ajoutes au tableau, sinon tu ne fais rien.
- Tu effaces les marqueurs (en leur donnant une position de -1 par exemple).
- Tu repars de la ou tu étais, et tu recommence jusqu'à tomber sur la fin de la chaîne.
- Au sortir de la boucle, tu auras le tableau désiré.
Ensuite, quelques outils:
- Accéder à un élément du tableau: tab[0] => 1er élément, tab[1] => 2ème élément.
- Convertir une chaîne en entier: atoi
- Recopier une chaîne: strcpy, strncpy
- Pour ton tableau, donne lui simplement une grande taille. (Sauf si tu as déjà vu en cours les réallocations mémoires, auquel cas il te faut realloc)
Tu as maintenant tout ce qu'il faut pour résoudre cet exercice.
cs_Vylco
Messages postés14Date d'inscriptionjeudi 20 septembre 2007StatutMembreDernière intervention26 novembre 2009 11 nov. 2009 à 16:28
Lut Captain, tu pourrais jeter un oeil à ce que j'ai fais parce que j'ai des erreurs et j'ai des questions aussi
Est ce que sa à l'air correct déja ?
Ensuite chui un peu perdu avec les pointeurs et du coup sa me donne quelque erreur genre
error C2296: '*' : non conforme, l'opérande gauche est du type 'int (__cdecl *)(int)'
error C2296: '*' : non conforme, l'opérande gauche est du type 'size_t (__cdecl *)(const char *)'
error C2297: '*' : non conforme, l'opérande droit est du type 'char *'
Merci d'avance pour les eclaircissements
void Extraire_Num(char *une_chaine)
{
int i,mdeb,mfin,j;
int tab[100];
char chtemp;
j=0;
//parcours de la chaine de caractère
for(i=0;i<strlen(une_chaine);i++)
{
//si on tombe sur un chiffre
if (isdigit*(une_chaine[i]))
{
//on affecte le marqueur de début par l'indice
mdeb=i;
//tant qu'on est pas à la fin de la chaine ou que l'on ne rencontre pas de caractère
while(mdeb<strlen*(une_chaine) && !isdigit*(une_chaine[j]))
{
//le marqueur de fin prend l'indice
mfin=j;
}
//on parcours alors la chaine entre nos 2 marqueurs
for(mdeb<mfin)
{
strcat(chtemp,*une_chaine[i]);
}
//si le chiffre dans la chaine temporaire est >10 et <30
if(atoi(chtemp)>10 && atoi(chtemp)<30)
{
//on copie le nombre dans le tableau
tab[j]=atoi(chtemp);
j++;
chtemp=null;
}
//on affecte le compteur i avec le marqueur de fin
i=mfin;
}
}
}
Vous n’avez pas trouvé la réponse que vous recherchez ?
cptpingu
Messages postés3837Date d'inscriptiondimanche 12 décembre 2004StatutModérateurDernière intervention28 mars 2023124 11 nov. 2009 à 16:47
Pourquoi mets tu des étoiles partout ?
"if (isdigit*(une_chaine[i]))" devrait être "if (isdigit(une_chaine[i]))".
De plus : "char chtemp;" est un caractère, donc tu ne peux pas le mettre à "null" (en plus c'est censé être NULL en majuscule).
while(mdeb<strlen*(une_chaine) && !isdigit*(une_chaine[j]))
{
//le marqueur de fin prend l'indice
mfin=j;
}
Ici, tu ne dois pas utiliser j, mais i. De plus tu n'incrémentes pas i, donc tu auras une boucle infinie.
//on parcours alors la chaine entre nos 2 marqueurs
for(mdeb<mfin)
{
strcat(chtemp,*une_chaine[i]);
}
Non, inutile de faire un parcours. Il suffit juste de faire une copie d'une certaine taille, en partant d'un certain indice (via strncpy). Vu que tu n'as pas du voir les pointeurs, on va conserver ta méthode.
Pour que tu puisse faire un strcat, chtemp doit être un chaîne de caractère, et non un caractère.
cs_Vylco
Messages postés14Date d'inscriptionjeudi 20 septembre 2007StatutMembreDernière intervention26 novembre 2009 11 nov. 2009 à 17:20
J'ai etudieé les pointeurs mais jme perds toujours un peu qd je les utilises , genre quand est ce qu'on doit mettre une * et quand faut pas en mettre, sinon la fonction strncpy m'a l'air plus adaptée mais je vois pas comment l'utilisée ici.
Sinon jai effectué les changements ce qui donne :
void Extraire_Num(char *une_chaine)
{
int i,mdeb,mfin,j;
int tab[100];
char chtemp[100];
j=0;
//parcours de la chaine de caractère
for(i=0;i<strlen(une_chaine);i++)
{
//si on tombe sur un chiffre
if (isdigit(une_chaine[i]))
{
//on affecte le marqueur de début par l'indice
mdeb=i;
i++;
//tant qu'on est pas à la fin de la chaine ou que l'on ne rencontre pas de caractère
while(mdeb<strlen(une_chaine) && !isdigit(une_chaine[i]))
{
//le marqueur de fin prend l'indice
mfin=i;
i++;
}
//on parcours alors la chaine entre nos 2 marqueurs
for(mdeb<mfin)
{
strcat(chtemp,une_chaine[i]);
}
//si le chiffre dans la chaine temporaire est >10 et <30
if(atoi(chtemp)>10 && atoi(chtemp)<30)
{
//on copie le nombre dans le tableau
tab[j]=atoi(chtemp);
j++;
chtemp=NULL;
}
}
}
}
cptpingu
Messages postés3837Date d'inscriptiondimanche 12 décembre 2004StatutModérateurDernière intervention28 mars 2023124 12 nov. 2009 à 11:04
J'ai etudieé les pointeurs mais jme perds toujours un peu qd je les utilises , genre quand est ce qu'on doit mettre une * et quand faut pas en mettre, sinon la fonction strncpy m'a l'air plus adaptée mais je vois pas comment l'utilisée ici
Lis ceci:
http://0217021.free.fr/Cours/pointeurs.pdf
(Adaptation en C d'un tuto que j'avais écrit en Delphi pour ce site).
Tu as encore pas mal de petit erreur de type. La fonction strcat est mal utilisé. Je t'invite à lire le pdf, et à essayer d'utiliser strncpy, qui est plus adapté.
for(mdeb<mfin)
{
Tu es sur de ne pas vouloir un while ? Parce qu'un for écrit comme cela, ce n'est pas possible.
cs_Vylco
Messages postés14Date d'inscriptionjeudi 20 septembre 2007StatutMembreDernière intervention26 novembre 2009 12 nov. 2009 à 15:13
yo captain, bon j'ai lu ton pdf et j'ai essayé d'améliorer mon code. J'obtiens plus d'erreur à la compilation mais dès que je tape une chaine dans mon scanf j'ai une erreur de type violation d'accés de lecture.
Aussi quand je donne un parametre a ma fonction Extraire_Num(*ch)je dois mettre char devant sinon j'obtiens une erreur:
'Extraire_Num' : identificateur introuvable
Je dois laisser char tu crois ? bref sa me parait bizard.
Sinon j'ai une question bete je fais comment pour afficher mon tableau (tab) une fois la fonction effectuée ?
Merci encore pour ton aide ^^
void main()
{
char *ch;
printf("saisir une chaine alphanumerique\n");
scanf("%s",&ch);
char Extraire_Num(*ch);
}
void Extraire_Num(char *une_chaine)
{
int i,mdeb,mfin,j,k;
int tab[100];
char *chtemp;
chtemp=(char*)malloc(100);
j=0;
//parcours de la chaine de caractère
for(i=0;i<strlen(une_chaine);i++)
{
//si on tombe sur un chiffre
if (isdigit(une_chaine[i]))
{
//on affecte le marqueur de début par l'indice
mdeb=i;
i++;
//tant qu'on est pas à la fin de la chaine ou que l'on ne rencontre pas de caractère
while(mdeb<strlen(une_chaine) && !isdigit(une_chaine[i]))
{
//le marqueur de fin prend l'indice
mfin=i;
i++;
}
//on parcours alors la chaine entre nos 2 marqueurs
while(mdeb<mfin)
{
strncpy(chtemp,&une_chaine[mdeb],100);
mdeb++;
}
//si le chiffre dans la chaine temporaire est >10 et <30
if(atoi(chtemp)>10 && atoi(chtemp)<30)
{
//on copie le nombre dans le tableau
tab[j]=atoi(chtemp);
j++;
chtemp="";
}
}
}
free(chtemp);
}
Oulah, faut relire le pdf :). Si tu n'alloues pas de mémoire, il ne peut rien mettre dedans.
Ici, inutile d'allouer quoi que ce soit. On va la mettre en dur.
char ch[256];
printf("saisir une chaine alphanumerique\n");
scanf("%s", ch); /* Pas de &, puisque ch n'est pas une variable scalaire (normal), mais un tableau, donc un pointeur */
char Extraire_Num(*ch); /* A effacer, ça n'a rien à faire là ! */
Tu mets ton main, en dessous de la fonction Extraire_Num.
Pour strncpy, il faut faire une soustraction de marqueur, et donc remplacer tes marqueurs de position par des marqueurs d'adresse (quoi qu'on puisse le faire en position).
cs_Vylco
Messages postés14Date d'inscriptionjeudi 20 septembre 2007StatutMembreDernière intervention26 novembre 2009 12 nov. 2009 à 18:21
ptain tu gère , sa marche sauf que sa me renvoit un résultat bizard, sa doit venir comme tu dit de strncpy.
tu peux m'expliquer ce que tu veux dire par "Pour strncpy, il faut faire une soustraction de marqueur, et donc remplacer tes marqueurs de position par des marqueurs d'adresse (quoi qu'on puisse le faire en position). " parce que j'ai beau chercher je vois pas comment faire.
cptpingu
Messages postés3837Date d'inscriptiondimanche 12 décembre 2004StatutModérateurDernière intervention28 mars 2023124 12 nov. 2009 à 18:43
Attention, non testé:
strncpy(chtemp, une_chaine + mdeb, mfin - mdeb);
/* une_chaine + mdeb => On commence à copier la chaine "une_chaine", en partant de "mdeb" caractère */
/* Ex: Si l'adresse de la chaine "une_chaine" est 0x00100, alors "une_chaine + mdeb" donnera "0x00100 + mdeb". */
/* On n'essaie pas d'obtenir le caractère à la position mdeb, mais d'obtenir l'adresse du premier caractère (pas sa valeur, mais ou il est placé en mémoire). Ce qui équivaut à donné l'endroit ou commence la sous-chaine en mémoire */
/* mfin - mdeb => taille du morceau de la chaine à récupérer, logique, non :p ? */
/* Ex: Si le premier caractère d'une chaine est à l'adresse 0x00100 et le dernier (caractère terminal '\0') à l'adresse 0x00108, alors la chaîne fera 8 caractères sans compter le caractère terminal '\0' (0x00108 - 0x00100 = 8) */
Ca devrait le faire, mais encore une fois je n'ai pas testé.
Ta methode me donne pas d'erreur a la compilation mais j'ai toujours le meme resultat quand je fais un printf de mon tableau tab :1244084, sa doit etre lié au fait que le printf de chtemp a la fin du while me donne un truc du genre 1=================================²²²²
Autrement un printf de mdeb et mfin me donne les bons indices par contre (ya au moins un truc qui marche ).
jte redonne mon code en entier au cas ou j'aurai foiré qque part :
void Extraire_Num(char *une_chaine)
{
int i,mdeb,mfin,j,k;
int tab[100];
char *chtemp;
chtemp=(char*)malloc(100);
j=mdeb=mfin=0;
//parcours de la chaine de caractère
for(i=0;i<strlen(une_chaine);i++)
{
//si on tombe sur un chiffre
if (isdigit(une_chaine[i])!=0)
{
//on affecte le marqueur de début par l'indice
mdeb=i;
i++;
printf("indice de debut %d \n",i);
//tant qu'on est pas à la fin de la chaine ou que l'on ne rencontre pas de caractère
while(mdeb<strlen(une_chaine) && isdigit(une_chaine[i])!=0)
{
//le marqueur de fin prend l'indice
mfin=i;
i++;
}
printf("indice de fin %d\n",i);
//on parcours alors la chaine entre nos 2 marqueurs
while(mdeb<mfin)
{
strncpy(chtemp, une_chaine + mdeb, mfin - mdeb);
mdeb++;
}
printf("%s\n",chtemp);
//si le chiffre dans la chaine temporaire est >10 et <30
if(atoi(chtemp)>10 && atoi(chtemp)<30)
{
//on copie le nombre dans le tableau
tab[j]=atoi(chtemp);
j++;
chtemp="";
}
}
}
free(chtemp);
printf("%d",tab);
getch();
}
void main()
{
char ch[256];
printf("saisir une chaine alphanumerique\n");
scanf("%s",ch);
Extraire_Num(ch);
}
cs_Vylco
Messages postés14Date d'inscriptionjeudi 20 septembre 2007StatutMembreDernière intervention26 novembre 2009 13 nov. 2009 à 17:52
yo captain, sa marche nikel j'ai remis tout en ordre et remis des commentaires maintenant c'est propre . Encore merci pour ton aide et passe un bon week end