Récupérer une chaîne de caractère dans un fichier

Récupérer une chaîne de caractère dans un fichier - Ada - Programmation

Marsh Posté le 16-05-2006 à 18:23:33    


Citation :


"Actuellement j'essaie de lire un fichier pour récupérer son contenu, en Out tel que l'écran standard pour commencer."


 
Plus précisément j'essaie de lire le fichier, identifier les caractères ou mots (c'est une chaine de caractères ou 'string' :) ) (<lettre>['_'][<chiffre>] en bnf) lus dans le fichier pour les extraires en sortie standard, par l'exemple :
 
admettons un fichier 'toto.txt' avec les lignes suivantes =>

--debut du fichier 'toto.txt'

ligne 1
ligne 2
ligne 3
-- fin du fichier 'toto.txt'
 
le résultat devrait me donner dans une sortie standard tel que l'écran:
 
ligne 1
ligne 2
ligne 3
 
Mais comme tu l'as remarqué je ne déclare peut être pas ce qu'il faut au bon endroit, on est le stupid_coder ou on ne l'est pas, ce n'est pas un choix mais une réalité....
 
Bref, je me demandais si je n'avais pas oublié des déclarations dans le type, ou mauvais type au mauvais endroit.
 
Aussi, j'ai tenté en vain de trouver une solution qui puisse prendre directement le nombre de caractères sur une ligne pour ensuite la récupérer dans l'extraction, en vue de la contenir dans un tableau pour plus tard:
 
exemple:
extrait du cours de génie logiciel de Daniel Feneuille, qui soulève le problème de connaitre le nombre de caractères d'une chaîne :
Je cite: " Comment affecter une chaîne à une autre chaîne si on ne connait pas sa longueur ?
[...] soit l'expression : t_jour'image(jour) [...]. Ce résultat ne porte pas en lui sa longueur ! Comment affecter cette chaîne à un evariable CHAINE_QUELCONQUE de typt T_STR sans savoir le nombre de caractères ?
 
long_chaine := t_jour'image(jour)'length;-- récupère la taille du STRING
CHAINE_QUELCONQUE(1..long_chaine):=t_jour'image(jour); --vraie affectation "
 
Pour le manque de précision je vous invite à lire le cours n°4 "Les STRING" à l'adresse suivante:
https://libre2.adacore.com/french_courses/
 
Et bien c'est une jolie formule mais j'ai un peu de mal là.
long_chaine récupère la taille de l'image de jour, pourquoi l'attribut image ?
 
"IMAGE permet de convertir un symbole de type énumératif en la chaîne
de caractères associée".
 
Dois-je faire de même pour le fichier, convertir les symboles en caractères associés ?


Message édité par stupid_coder le 17-05-2006 à 00:38:47

---------------
...pour les miracles ? prévoir un délai !
Reply

Marsh Posté le 16-05-2006 à 18:23:33   

Reply

Marsh Posté le 16-05-2006 à 21:13:20    

Salut stupid_coder,
Je ne sais pas pourquoi l'erreur End_Of_File est levée, je vais cherché un peut mais il y a Matrix ce soir à la télé
J'ai essayé get_line, ça marche ?
 
tu ne peut pas utiliser Length sans get_line !
 
Si tu n'affiche rien c'est normal, tu ne fais aucun appel a une procedure d'affichage !

Reply

Marsh Posté le 16-05-2006 à 21:29:35    

j'ai déjà eu le problème de End_Error ; Je ne sais pas le resoudre ; End_Error est levée losrqu'on assai de lire audela de la fin du fichier;
 :heink:  
donc soit on lis caractere par caractere et la End_Of_Line marche comme on s'y attent,
          soit tu traite l'exception et ça roule ; c'est une exception a la con ; c'est tout.

Reply

Marsh Posté le 16-05-2006 à 21:55:47    

Bonjour Jovalise,
 
Comment sais tu que c'est l'erreur end_of_file qui lève l'erreur ?
 
Le changement suivant :
 
while not(End_Of_File(F)) loop--tant que pas fin de fichier
      while not(end_of_line)loop
      get(f,line);
            for I in 1..Length loop
         if Line(i)='I' then
            Get(F,Line);
            put(f,line);            
            end if;
            ......
 
me donne la possibilité de taper des caractères et ensuite génère l'erreur...
 
Je pensais aussi utiliser à la place de "while not" un "exit when" pour le "end_of_file" mais c'est pire...


---------------
...pour les miracles ? prévoir un délai !
Reply

Marsh Posté le 16-05-2006 à 23:52:06    

oui , pardon , j'ai fait une erreur, il falait lire : "Je ne sais pas pourquoi l'erreur End_Error est levée, j
 
mais que fais-tu en fait ? tu lis dans un fichier, et dans l'entré standard ? s'ai bizare ce que tu fait  

Reply

Marsh Posté le 17-05-2006 à 01:54:14    

j'ai édité le texte d'origine, pas très malin...


---------------
...pour les miracles ? prévoir un délai !
Reply

Marsh Posté le 17-05-2006 à 02:20:04    

Après quelques changements de type je peux affirmer :
 
if  (Line ='I')
 
est possible si line est un type charactère et non un sous type string (la comparaison '=' ne fonctionne pas sinon)


---------------
...pour les miracles ? prévoir un délai !
Reply

Marsh Posté le 17-05-2006 à 03:19:55    

Dernier post de la soirée ou premier de la matinée c'est selon...
 
Jovalise, j'ai extrait une partie intéressante quand tu m'as dit que je lisais dans le fichier et l'entrée standard...
 
for I in 1..Lg loop--lg:natural;
      Get(F,Line);--f:file_type;line:character;
      if  Line ='I'
      then  
get(f,car); --avec car:character;
put(car);
skip_line;--saut de ligne je pense
end if
...
 
les 3 lignes s'affichent consécutivement mais un message d'erreur sur les I/O_exception_end_error 396 aura raison de l'algo...
 
see u soon, bonne nuit à tous !


---------------
...pour les miracles ? prévoir un délai !
Reply

Marsh Posté le 17-05-2006 à 17:06:10    

Peut-tu mettre ton code ici, parceque honnêtement galérer plusieurs jours sur la lecture d'un fichier texte, c'est pas top... ;)

Reply

Marsh Posté le 18-05-2006 à 23:48:55    

Bonsoir tout le monde,
 
De retour avec des balises comme ça, la cafetière qui déborde dans tous les sens, mais plus pour longtemps...
 
Bref, j'ai une solution pour afficher qui fonctionne, je rappelle le contexte:
afficher les lignes d'un fichier sur la sortie standard.
 
Cependant la boucle me met dedans quand je l'utilise, donc c'est pas top...
 
lignes.txt
--debut fichier
a 1 2 3 4
B 4 6 7 8
c 9 10 11 12
--fin fichier
 
-- debut code
 

Code :
  1. with Ada.Text_Io;
  2. use Ada.Text_Io;
  3. --with Ada.Integer_Text_Io;
  4. --use Ada.Integer_Text_Io;
  5. with Ada.Text_Io;--Ada.Strings.Unbounded;
  6. with Ada.Float_Text_Io;
  7. use Ada.Float_Text_Io;
  8. --with Ada.Numerics.Elementary_Functions;
  9. --use Ada.Numerics.Elementary_Functions;
  10. --use Ada.Text_Io,Ada.Strings.Unbounded;
  11. with Ada.Characters.Handling;
  12. use Ada.Characters.Handling;
  13. procedure Lire_Fichier is
  14.    F   : File_Type;
  15.    Car : String (1 .. 100);
  16.    Lg  : Natural;
  17.    C   : Character;
  18.  
  19.   begin
  20.    Open (F,In_File,"lignes.txt" ); --ouverture d un fichier lignes
  21.   while not (End_Of_line(F)) loop -- la boucle pour chaque ligne
  22.         Get_line(F,Car,lg); -- on récupère l info ...
  23.         Put(Car(1..Lg)); -- ... pour l afficher
  24.       Skip_Line; --saut de ligne avec retour charriot
  25.     end loop;
  26.    Close (F);
  27. end Lire_Fichier;


 
--fin code
 
Le résultat donne ceci, une par une les lignes:
 
a 1 2 3 4
B 4 6 7 8
c 9 10 11 12
 
Un code parfait dans un monde parfait...
 
Cependant,néanmoins... je veux "identifier" chaque ligne par le caractère en début de ligne pour afficher le "contenu".
 
L'exemple ici est simplifié mais dans la réalité je peux avoir plusieurs 'a','b' ou 'c'...
 


---------------
...pour les miracles ? prévoir un délai !
Reply

Marsh Posté le 18-05-2006 à 23:48:55   

Reply

Marsh Posté le 19-05-2006 à 02:17:09    

Bon d'abord, il manque un new_line pour afficher ce que tu montres.
 
Ensuite : ça sert à quoi d'identifier une ligne par le caractère de début de ligne

Reply

Marsh Posté le 19-05-2006 à 21:07:02    

Bonjour apprentitux,
 
Bon je vais aller un peu plus loin dans les explications...
 
Actuellement le fait de lire dans un fichier est une prmière étape.
Ensuite, le contenu de ce fichier sera réutilisé plus tard dans mon algotithme
 
L'exemple que je donne ici est simplifiée :  
 
Le contenu utilisé est préformaté comme si nous avions ceci
exemple
 

a 01 01 2000


 
 'a' est un type représenté comme ceci
 

Code :
  1. type t_entrée is
  2. record
  3. r:t_jour; -- bien sure t_jour est subtype t_jour is natural range 1..31 ...
  4. s:t_mois; --...
  5. t:t_annee;--...
  6. end record


 
Donc suivant les lettre de début ici, a, qui représente l'année d'entrée dans une société,
 
je déclare une variable x de type t_entrée ce qui donne après affectation :
 

Code :
  1. x.r:=01;
  2. x.s:=01;
  3. x.t:=2000;


 
Donc chaque 'champs' a son utilité et ne peut être associé à autre chose.
Note que les valeurs "01" ne sont pas identiques: l'une correspond au jour et l'autre au mois...
 
Il y a les entrées mais on peut facilement imaginer les départs 'b'
 

Code :
  1. type t_depart is
  2. record
  3. x:t_jour;
  4. y:t_mois;
  5. z:t_annee;
  6. end record


 
et le fichier ressembler à ça :
 

a 01 01 2000
b 01 02 2001
a 01 12 2000
b 01 03 2003
a 01 04 1999
b ... ...  .....


 
Le plus rébarbatif ici c'est la phase de get et put qui est associé à chaques valeurs:
 
 
   

Code :
  1. Get(F,x.r);
  2.             Put (x.r);
  3.             Get(F,x.s);
  4.             Put (x.s);
  5.             Get(F,x.t);
  6.             Put (x.t);
  7.             Get(F,b.x);
  8.             Put (b.x);
  9.             Get(F,b.y);
  10.             Put (b.y);
  11.             Get(F,b.z);
  12.             Put (b;z);
  13.             Skip_Line;


 
Et ainsi de suite pour chaque 'lignes' identifiées par une lettre. Ce n'est pas ma volonté mais une contraite de traitement...
 
C'est déjà pas mal pour le moment, si manque d'explication, dites le moi...
 
Ma question, est il possible une sorte de bocle get ou put plus 'propre' ?
 

Reply

Marsh Posté le 19-05-2006 à 22:06:37    

apprentitux a écrit :

Bon d'abord, il manque un new_line pour afficher ce que tu montres.
 
Ensuite : ça sert à quoi d'identifier une ligne par le caractère de début de ligne


 
Pourkoi un new_line ? le contenu du fichier s'affiche...


---------------
...pour les miracles ? prévoir un délai !
Reply

Marsh Posté le 24-05-2006 à 21:51:48    

Bonsoir à tous,
 
Je me posais une question sur le package à utiliser pour manipuler un fichier en in_file avec des "character" à l'intérieur : sequential_io, direct_io ou simplement text_io ?
 
Je crois savoir que sequential_io et direct_io sont dans la catégorie binaire...


---------------
...pour les miracles ? prévoir un délai !
Reply

Marsh Posté le 24-05-2006 à 22:21:39    

stupid_coder a écrit :

Bonsoir à tous,
 
Je me posais une question sur le package à utiliser pour manipuler un fichier en in_file avec des "character" à l'intérieur : sequential_io, direct_io ou simplement text_io ?
 
Je crois savoir que sequential_io et direct_io sont dans la catégorie binaire...


Slaut stupid_coder,
 
une diference entre direct_io et sequential_io, c'est le faite que direct_io ouvre un fichier en acces direct et sequential_io en acces sequenciel.
une autre entre direct_io et sequential_io, ce sont les mode d'ouverture de fichier : in_file, out_file, append_file, pour sequential_io et text_io, et in_file, inout_file, et out_file pour direct_io,
un fichier text est lisible
les representation de direct_io, et sequential_io sont lessai a la discretion de (je sais plus qui)
 
edit : je corrige mes betises  :heink:


Message édité par Profil supprimé le 24-05-2006 à 22:25:26
Reply

Marsh Posté le 24-05-2006 à 23:08:03    

Bonsoir Jovalise,
 
Merci de ta réponse.
 
Cependant j'utilise comme tu as pu le constater plus haut, un fichier en in_file uniquement pour extraire sont contenu et le garder en mémoire. Donc plusieurs packages me sont proposés...
 
Je te donne ci-dessous le bout de code qui me fait frémir en ce moment...
 

Code :
  1. Open(F,In_File, "lignes" );
  2.    while not (End_Of_File(F)) loop
  3.       Get_Line(F,Str,Lg);--file_type/string(1..80)/natural
  4.       for I in 1..Lg loop
  5.          if I in str(1..1) /= ('I' or 'C' or 'L' or 'T' or 'S' or 'R') then --ici je veux passer à la ligne suivante si le premier carctère ne fait pas parti des caractères cités. ici ça bloque au '/=': 'inexpected relational operator'
  6.             Skip_Line;
  7. ...


 


---------------
...pour les miracles ? prévoir un délai !
Reply

Marsh Posté le 24-05-2006 à 23:37:14    

ben, wai, ben normal  [:666rip666]
 
edit j'delire   ;)


Message édité par Profil supprimé le 24-05-2006 à 23:39:20
Reply

Marsh Posté le 24-05-2006 à 23:42:37    

wai voila,
 
ça veut dire quoi  

Code :
  1. if I in str(1..1) /= ('I' or 'C' or 'L' or 'T' or 'S' or 'R') then

Reply

Marsh Posté le 24-05-2006 à 23:43:57    

le i in est de trop

Reply

Marsh Posté le 25-05-2006 à 00:09:08    


 
 
Les choses sérieuses commencent....
 
Je veux évaluer le premier caractère de la chaine.
Si c'est pas un 'I'... alors ligne suivante.
Mais...  
str:string(1..80):
'I':character:
la relation str /= 'I'  ne marche pas , car types différents... :pt1cable:  
Pourtant c'est comme une obligation de se tapper cette formulation:
 
"si le premier caractère de la ligne n'est pas une lettre majuscule, passer à la ligne suivante, ne touchez pas le 20 000 €..."  
 
Il y a aussi un blème avec les "or", y comprends pas ma façon de voir les choses, c'est ambêtant...  :heink:


---------------
...pour les miracles ? prévoir un délai !
Reply

Marsh Posté le 25-05-2006 à 00:32:54    

Pas bon ça...
 

Code :
  1. if Str(1..1) /= 'I' then


 
Il me dit que "non, ce soir tu te coucheras pas tôt, je te le promets..."  
 

Code :
  1. 'left operand has subtype of standard.string"
  2. "right operand has a character type"


 
donc evident standard.string /= character type pour le coup, je le sais, le lis, le vois mais suis incapable de vous dire pourquoi ! :pt1cable:  
 
j'essaie un str'image, str'value, je pense même qu'il me dit que je verrais même pas un bout de la couette là...


---------------
...pour les miracles ? prévoir un délai !
Reply

Marsh Posté le 25-05-2006 à 02:15:39    

il y a encore 3 caracteres de trop

Code :
  1. if Str(1) /= 'I' then
  2.   new_line;


Message édité par Profil supprimé le 25-05-2006 à 02:15:52
Reply

Marsh Posté le 27-05-2006 à 16:37:17    

stupid_coder a écrit :

Je veux évaluer le premier caractère de la chaine.
Si c'est pas un 'I'... alors ligne suivante.
Mais...  
str:string(1..80):
'I':character:
la relation str /= 'I'  ne marche pas , car types différents... :pt1cable:  
Pourtant c'est comme une obligation de se tapper cette formulation


Le type String en Ada est un tableau de caractères.
Tu veux comparer un tableau de caractères avec un caractère, tu vois pas comme un problème ??
Idem pour ta comparaison :

stupid_coder a écrit :

if Str(1..1) /= 'I' then


Tu compares un tableau de un caractère avec un caractère, du style : ['e'] = 'r'
 
Mon conseil sera donc le suivant :
Y a de très bons cours sur le net, donc étudies-les et arrêtes de poster ce genre de messages alors que le compilateur te donne des messages aussi explicites.
Ca se voit que tu débutes et on est tous passé par là, mais c'est pas te rendre service que de t'aider à compiler une simple affectation ou une comparaison de type primitifs..
 

stupid_coder a écrit :

Il y a aussi un blème avec les "or", y comprends pas ma façon de voir les choses, c'est ambêtant...  :heink:


 
Non c'est vrai le compilateur ne comprends pas ta façon de voir les choses...
Il est vraiment mal fait ...
Reprogrammes-le.

Reply

Marsh Posté le 28-05-2006 à 23:43:09    

apprentitux a écrit :


Il est vraiment mal fait ...
Reprogrammes-le.


 
Je me disais, tu as remarqué aussi...
 
Bon sérieux, voilà ce que j'ai qui me donne que du bonheur :
 

Code :
  1. --le type car est charactère :)
  2. begin
  3.    Open(F,In_File, "lignes.txt" );
  4.  
  5.       while not(end_of_line(f)) loop
  6.          
  7.             get(F,car);
  8.      
  9.           if car = 'I' or car= 'C' or car='L' or car= 'T' or car= 'S' or car= 'R' then
  10. ...


 
Je vais tester avec les caractères c,l,t,s et r et je vous dis si ça marche.
J'mets stupid_coder sur ma carte d'identité en tant que prénom si ça marche pas   :D


---------------
...pour les miracles ? prévoir un délai !
Reply

Marsh Posté le 30-05-2006 à 17:27:56    

Bonjour !
 
Bon je confirme ça fonctionne nickel ! j'ai eu chaud
 
petite précision sur les case:
 
y a t'il moyen de l'utiliser avec autre chose de des types discrets ?


---------------
...pour les miracles ? prévoir un délai !
Reply

Marsh Posté le 30-05-2006 à 20:57:38    

Bonsoir
peut-etre as-tu déjàs repondu a ta question, mais la reponse est non
 :jap:

Reply

Marsh Posté le 31-05-2006 à 20:06:20    

Bonjour Jovalise,
 
Donc si je veux extraires dans un fichier une ligne, pour l'utilisation d'un case, il ne faut pas rencontrer de float ?
Je vais peut être dire une anerie, mais pourquoi  avoir la possibilité de faire un
 

Code :
  1. integer'image()


 
et ne pas avoir d'équivalant en float ?


---------------
...pour les miracles ? prévoir un délai !
Reply

Marsh Posté le 31-05-2006 à 21:44:04    

je vois pas le rapport avec le "case"
 
l'attribut image existe aussi pour les float, pour tous les scalaires en fait, donc les réels et les discrets

Reply

Marsh Posté le 01-06-2006 à 00:12:19    

le case ait à priori  utilisé uniquement avec les discrets...


---------------
...pour les miracles ? prévoir un délai !
Reply

Marsh Posté le 01-06-2006 à 09:28:56    

effectivement, mais quel rapport avec l'attribut image ?

Reply

Marsh Posté le 02-06-2006 à 12:24:22    


Idem pour moi : je comprends rien à ce que dit stupid_codeur...
 
Et mec ! Arrètes les énigmes et essaye de t'exprimer clairement, on t'aidera plus vite parceque là, on dirait vraiment un dialogue de sourd!

Reply

Marsh Posté le 07-06-2006 à 10:57:48    

J'm comprends c'est le principal et le projet est terminé.
Merci pour votre aide.


---------------
...pour les miracles ? prévoir un délai !
Reply

Marsh Posté le 07-06-2006 à 13:26:41    

De rien, mais exprimes-toi mieux la prochaine fois ...
 
... De +, quand tu postes sur un forum, le principal n'est justement pas que tu te comprennes ... car ça peut servir à d'autres.


Message édité par apprentitux le 07-06-2006 à 13:28:08
Reply

Marsh Posté le 08-06-2006 à 21:57:05    

Humour au 8ème degrés apprentitux...
Il faut rebooter des fois !


---------------
...pour les miracles ? prévoir un délai !
Reply

Marsh Posté le 09-06-2006 à 10:01:07    

Non, moi je rigole jamais
 
http://www.journaled.com/MA/Aikido/SSeagal/sseagal.jpg


Message édité par apprentitux le 16-06-2006 à 11:46:10
Reply

Marsh Posté le    

Reply

Sujets relatifs:

Leave a Replay

Make sure you enter the(*)required information where indicate.HTML code is not allowed