Trie sur fichiers

Trie sur fichiers - Perl - Programmation

Marsh Posté le 01-06-2008 à 22:14:11    

Bonjour, je viens de me mettre à Perl et encore s'est beaucoup dire  :wahoo:  
J'ai un peu de mal avec la façon dont Perl organise les choses et j'aimerais votre aide a travers un exemple simple pour m'aider à comprendre.
 
J'ai deux fichiers avec des IP et des informations à leurs sujets tel que leurs sous-réseaux, leur lieu d'attribution et la dernière date de mise en place. Dans un fichier les données sont récentes et sûres et dans l'autres les informations sont plus complètes mais certaines IP sont down.
 
Ce que je veux faire c'est selon les IP valides du fichier récent, récupérer des informations de mon fichier obsolète.
 
Mes fichiers sont de la forme suivantes :
- Fichier récent : IP [espace] informations inutiles [espace] date de dernière connection
- Fichier obsolète : IP [espace] lieu [espace] réseau [espace] informations inutiles [espace] date [espace]

Reply

Marsh Posté le 01-06-2008 à 22:14:11   

Reply

Marsh Posté le 02-06-2008 à 02:08:19    

Si je comprends bien, les seuls espaces sur une ligne sont pour separer les champs? pas d'espace dans lieu ou informations inutiles? chaque IP n'apparait qu'une fois?
Si oui, tu peux parser Fichier obsolète et Fichier recent facilement, avec une expression reguliere ad-hoc.
Tu crée un hash dont la key est la valeur de l'IP, et la value , une reference sur un hash anonyme avec les cles lieu, reseau, info-inutiles, date correspondant a une ligne parsée.
Ca te permet ensuite quand tu parses Fichier recent, d'acceder rapidement aux infos qu'il y avait dans Fichier obsolète pour une IP de Fichier recent, et d'utiliser ces infos.
A+,


Message édité par gilou le 02-06-2008 à 02:09:36

---------------
There's more than what can be linked! --    Iyashikei Anime Forever!    --  AngularJS c'est un framework d'engulé!  --
Reply

Marsh Posté le 02-06-2008 à 18:50:08    

Très bien je vais faire des recherches sur la fonction pour parser ...
Je suis d'accord pour le hash, toi tu créerais qu'un seul hash ? qui récupère l'IP du fichier récent puis fouille dans oboslète pour récuperer les infos que l'on met dans le hash ...
Un truc du genre : $hash[$ip] = split(/s+/)  :ouch:  
Et comment j'affiche mes résultats ... j'ai du mal avec les tableau  :(  
Merci de ton aide  :hello:


Message édité par seb-info le 02-06-2008 à 18:51:02
Reply

Marsh Posté le 02-06-2008 à 22:48:37    

Ce genre de truc: IP [espace] lieu [espace] réseau [espace] informations inutiles [espace] date [espace] Ou tu sais que tu n'as que 5 espaces dans la ligne qui separent les champs, ca se parse en s'inspirant de ceci:
my %myhash;
if ($line =~ /^(\S+)\s+(\S+)\s+(\S+)\s+(\S+)\s+(\S+)\s+$/) {
           $myhash{$1} = {'lieu' => $2, 'reseau' =>$3, 'info_inutile' => $4, 'date' => $5};
}
A+,


Message édité par gilou le 02-06-2008 à 22:50:26

---------------
There's more than what can be linked! --    Iyashikei Anime Forever!    --  AngularJS c'est un framework d'engulé!  --
Reply

Marsh Posté le 04-06-2008 à 23:06:42    

Merci pour le bout de code ça m'a beaucoup aidé. Cependant je bloque sur l'affichage du contenu du hash. En revanche les parties récupérées avec la regex sont bonnes. Voici mon code :
 

Code :
  1. #!/usr/bin/perl -w
  2. open (SRV, "C:\\srv-list.txt" ) or die "erreur $!\n";
  3. my %tablo;
  4. while ($ligne = <SRV> ) {
  5. if ($ligne =~ /^(\S+)\s+(\S+)\s+\S+\s+\S+\s+\S+\s+(\S+)$/) {
  6.  $tablo{$1} = {'type' => $2, 'pays' =>$3};
  7. #  print "mes saisies : $1, $2, $3\n\n";
  8. }
  9. }
  10. print $tablo{'11.11.11.11:80'};
  11. close SRV;


Ce code n'affiche pas les informations sur l'IP. A l'éxécution j'ai l'erreur suivante :
 
Use of an uninitialized value in print at C:\scriptt.pl line 11, <SRV> line 477.


Message édité par seb-info le 04-06-2008 à 23:07:07
Reply

Marsh Posté le 05-06-2008 à 00:11:43    

J'ai l'impression que le pb est au niveau de la clé mise dans $tablo et qu'elle est considérée comme différente de '11.11.11.11:80' et donc que quand tu fais $tablo{'11.11.11.11:80'} il ne trouve rien pour cette clé.
 
Fais une impression de keys(%tablo) pour voir comment y sont les clés.
il faut peut être faire $tablo{"$1"} = {'type' => $2, 'pays' =>$3}; ou un truc de ce genre
 
Si ca ne suffit pas, Pour voir comment $tablo a été exactement rempli, dumpe sa valeur.
use Data::Dumper;
print Dumper($tablo);
 
Notes que pour accéder aux valeurs, dans tablo, il faudra faire:
print $tablo{'11.11.11.11:80'}->{'type'} et  print $tablo{'11.11.11.11:80'}->{'pays'}
car $tablo{'11.11.11.11:80'} est une reference a un hash anonyme, et print $tablo{'11.11.11.11:80'} devrait juste afficher l'adresse de ce hash anonyme.
 
A+,


Message édité par gilou le 05-06-2008 à 00:14:02

---------------
There's more than what can be linked! --    Iyashikei Anime Forever!    --  AngularJS c'est un framework d'engulé!  --
Reply

Marsh Posté le 05-06-2008 à 02:05:22    

En fait, j'ai testé ton code (adapté) avec un petit exemple:

Code :
  1. #!/usr/bin/perl
  2. use warnings;
  3. use strict;
  4. my %tablo;
  5. open my $SRV, '<', "srv.txt" or die "erreur $!\n";
  6. while (<$SRV> ) {
  7.     if (/^(\S+)\s+(\S+)\s+\S+\s+\S+\s+\S+\s+(\S+)$/) {
  8.         $tablo{$1} = {'type' => $2, 'pays' =>$3};
  9.     }
  10. }
  11. print $tablo{'11.11.11.11:80'}->{'type'}, " ",
  12.     $tablo{'11.11.11.11:80'}->{'pays'}, "\n";
  13. close $SRV;


et srv.txt:

Citation :

11.11.11.11:80 Paris freenet blablabla 9-1-1 blablabla
11.11.11.12:80 Lilles Oleane blablabla 9-1-3 blablabla


Et ca marche sans pb.
La seule maniere d'avoir l'erreur que tu donnes, c'est quand il n'y a pas de match entre la ligne et l'expression reguliere (ici: 6 champs texte separes par des blancs)
Donc soit ton expression reguliere n'est pas bonne, soit tu utilises une clé absentedu fichier parsé.
A+,


---------------
There's more than what can be linked! --    Iyashikei Anime Forever!    --  AngularJS c'est un framework d'engulé!  --
Reply

Marsh Posté le 05-06-2008 à 14:02:33    

Merci pour les explications je vais regarder comment utiliser les fonctions.
Le code que tu as fait ne fonctionne pas sur ma machine. J'ai l'erreur :
 
Use of an uninitialized value in print at C:\trie.pl line 12, <$SRV> line 477.
 
Je vais regarder du côté des clés du hash, je reposterais ce soir.

Message cité 1 fois
Message édité par seb-info le 05-06-2008 à 14:03:22
Reply

Marsh Posté le 05-06-2008 à 14:10:49    

l'exemple que Gilou t'a donné fonctionnait uniquement avec le fichier mis en exemple. C'est pour ça que la clé est en dur dans le print.  
Si tu veux toutes les clés de ta hash, remplace les lignes 12 et 13 par:

Code :
  1. foreach my $ip (keys %tablo){
  2. print $tablo{$ip}->{'type'}, " ",  $tablo{$ip}->{'pays'}, "\n";
  3. }


Message édité par anapajari le 05-06-2008 à 14:12:03

---------------
Software and cathedrals are much the same - first we build them, then we pray.
Reply

Marsh Posté le 05-06-2008 à 15:01:41    

En fait, je pense qu'il recupere des cles dans nouveau fichier, et veut recuperer des valeurs dans ancien fichier.
Mais s'il teste avec une clé (donc IP) présente dans le nouveau, mais pas dans l'ancien, ca va lui faire cela.
Il faut qu'il teste si la clé $ip existe avec un
if (exists $tablo{$ip})
avant de vouloir en utiliser ses valeurs.
A+,


---------------
There's more than what can be linked! --    Iyashikei Anime Forever!    --  AngularJS c'est un framework d'engulé!  --
Reply

Marsh Posté le 05-06-2008 à 15:01:41   

Reply

Marsh Posté le 05-06-2008 à 15:05:20    

seb-info a écrit :

Merci pour les explications je vais regarder comment utiliser les fonctions.
Le code que tu as fait ne fonctionne pas sur ma machine. J'ai l'erreur :
 
Use of an uninitialized value in print at C:\trie.pl line 12, <$SRV> line 477.
 
Je vais regarder du côté des clés du hash, je reposterais ce soir.

C'est plutoit qu'il a rien matché dans l'expression reguliere pour l'IP 11.11.11.11:80
Donc soit l'IP ne figure pas dans le fichier $SRV, soit la ligne ou elle figure n'est pas conforme a ce qu'attend l'expression reguliere.
A+,


---------------
There's more than what can be linked! --    Iyashikei Anime Forever!    --  AngularJS c'est un framework d'engulé!  --
Reply

Sujets relatifs:

Leave a Replay

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