PERL_Tri et concaténantion

Amine7592 Messages postés 28 Statut Membre -  
Amine7592 Messages postés 28 Statut Membre -
Bonjour,

J'aimerai concaténer plusieurs fichiers ( dans l'ordre) en utilisant le langage PERL ?

Exemple des fichiers à concaténer :

A_1980_AB11_1001.txt
A_1980_AB11_1003.txt
A_1980_AB11_1002.txt
A_1980_2AB12_1001.txt
A_1980_AB13_1001.txt
A_1980_2AB12_1002.txt

Dans le fichier final, je dois avoir le contenu des fichiers ci-dessous ( et dans l'ordre) :

A_1980_AB11_1001.txt
A_1980_AB11_1002.txt
A_1980_AB11_1003.txt
A_1980_2AB12_1001.txt
A_1980_2AB12_1002.txt
A_1980_AB13_1001.txt

Par avance, je vous remercie pour votre aide.

Amine.

7 réponses

Résumé de la discussion

Le besoin est de concaténer plusieurs fichiers en Perl dans un ordre précis, comme A_1980_AB11_1001.txt, A_1980_AB11_1003.txt et A_1980_2AB12_1002.txt, pour produire un fichier final dont le contenu suit un ordre défini. Des solutions évoquées incluent l’énumération des fichiers d’un répertoire, le filtrage par motif tel que A_2012_*, puis le tri pour imposer l’ordre souhaité et l’écriture des contenus dans le fichier de sortie. En pratique, basename et dirname permettent de séparer chemin et nom, et un tri lexicographique via sort peut ordonner les noms selon leur composition numérique, avec des sauts de ligne selon le besoin.

Généré automatiquement par IA
sur la base des meilleures réponses
  1. Amine7592 Messages postés 28 Statut Membre
     
    Personne pour m'aider :(((
    0
  2. valentin2703 Messages postés 185 Statut Membre 9
     
    Bonjour,

    Si tu veut trier tes fichiers, je pense que la meilleur façons de faire est de lister le contenu de ton dossier avec une fonction et ensuite de les trier toi même.
    Une fois que tu les a trié, il ne te reste plus qu'à les ouvrir un par un pour tout entrer dans un seul fichier.

    Une fonction pour lister tous les fichiers d'un dossier :
    sub listDirectory { 
     my ($repertoire) = @_; 
     my @fichiers = (); 
     opendir (my $rep_fh, $repertoire) or die "impossible d'ouvrir le repertoire $repertoire\n"; 
     my @file_rep = grep { !/^\.\.?$/ } readdir($rep_fh); 
     closedir ($rep_fh); 
     foreach my $nom (@file_rep) { 
      if (-f "$repertoire/$nom") { push (@fichiers, $nom); } 
     } 
     return @fichiers; 
    }
    0
  3. Amine7592 Messages postés 28 Statut Membre
     
    Merci beaucoup pour cette réponse. malheureusement, je ne suis pas un spécialiste du PERL et ne comprends pas l'ensemble de votre programme.

    Pour exécuter votre programme, je dois :
    - Définir une variable "repertoire" : \\Home\TEST
    - Définir la variable "fichiers" ( le répertoire final)

    Est-ce que c'est bien ça ?

    Encore, je vous remercie beaucoup.

    sub listDirectory {
    my ($repertoire) = @_;
    my @fichiers = ();
    opendir (my $rep_fh, $repertoire) or die "impossible d'ouvrir le repertoire $repertoire\n";
    my @file_rep = grep { !/^\.\.?$/ } readdir($rep_fh);
    closedir ($rep_fh);
    foreach my $nom (@file_rep) {
    if (-f "$repertoire/$nom") { push (@fichiers, $nom); }
    }
    return @fichiers;
    }
    0
  4. valentin2703 Messages postés 185 Statut Membre 9
     
    Il suffit de lancer la fonction avec comme ceci :
    my $repertoire = "TON DOSSIER";
    my @fichiers = &listDirectory($repertoire);

    Sachant que la variable $repertoire contient le chemin vers le dossier que tu veut lister.
    Ensuite, la fonction va te retourner un tableau (@fichiers) qui contient tous les fichiers du dossier.
    0
  5. Vous n’avez pas trouvé la réponse que vous recherchez ?

    Posez votre question
  6. heyquem Messages postés 808 Statut Membre 131
     
    Salut,

    J'ai écrit le code en Python.

    J'ai d'abord créé 6 fichiers avec les contenus suivants:

    - nom du fichier: AB11_1001
    - contenu du fichier:
    blablabli
    blablabla
    contenu du fichier AB11_1001
    balablabalablalblabli

    - nom du fichier: AB11_1003
    - contenu du fichier:
    karakako
    contenu du fichier AB11_1003
    kakakukiko

    - nom du fichier: AB11_1002
    - contenu du fichier:
    dudurududu
    contenu du fichier AB11_1002
    dododudud

    - nom du fichier: 2AB12_1001
    - contenu du fichier:
    mumumumimimim
    contenu du fichier 2AB12_1001
    mamamamimummmumim

    - nom du fichier: AB13_1001
    - contenu du fichier:
    xixixixixixixixixi
    contenu du fichier AB13_1001
    xuxuxuxuuxxuxexexexexe

    - nom du fichier: 2AB12_1002
    - contenu du fichier:
    taratatattat
    ttatrotototerottotot
    contenu du fichier 2AB12_1002
    tttttttaaaaaaratatatatta

    Et le code qui crée un fichier cumulatif des contenus de ces fichiers dans un ordre dépendant de leur nom:

    from os import listdir 
    import re 
    
    regx = re.compile('[_\d]+(?=\.)') 
    
    li = listdir('I:\\Prov Python') 
    li.sort(key=lambda x: regx.search(x).group()) 
    
    with open('I:\\Prov Python\\cumul.txt','w') as cumul: 
        for filename in li: 
            with open('I:\\Prov Python\\' + filename,'r') as f: 
                cumul.write(f.read())


    Bien sûr, la regex est fonction de ce que j'ai pensé plausible comme critère de tri des noms de fichiers sur la base de seulement 6 noms. Pour d'autres règles, il faudra une regex différente.

    Après exécution, j'obtiens le fichier cumul.txt avec le contenu suivant:

    blablabli
    blablabla
    contenu du fichier AB11_1001
    balablabalablalblabli

    dudurududu
    contenu du fichier AB11_1002
    dododudud

    karakako
    contenu du fichier AB11_1003
    kakakukiko

    mumumumimimim
    contenu du fichier 2AB12_1001
    mamamamimummmumim

    taratatattat
    ttatrotototerottotot
    contenu du fichier 2AB12_1002
    tttttttaaaaaaratatatatta

    xixixixixixixixixi
    contenu du fichier AB13_1001
    xuxuxuxuuxxuxexexexexe

    Je sais que tu as parlé de Perl, mais comme tu dis ne pas le connaître, ce n'est peut être que l'objectif qui t'intéresse, sans être attaché à un langage en particulier.
    0
  7. Amine7592 Messages postés 28 Statut Membre
     
    Je pense que je n'ai pas très bien décris le besoin :
    le but est de concatener le contenu des fichiers et à voir un "fichier_concat_final" qui contient le contenu de l'ensemble des fichiers.

    Merci encore pour votre aide.
    0
    1. valentin2703 Messages postés 185 Statut Membre 9
       
      C'est exactement ce que viens de te proposer heyquem, il récupère le contenu de tous tes fichiers pour le mettre dans un fichier cumul.txt.
      0
    2. heyquem Messages postés 808 Statut Membre 131
       
      Merci de m'avoir compris valentin :)
      0
    3. Amine7592 Messages postés 28 Statut Membre
       
      Bonjour heyquem,

      MERCI pour votre aide. Je n'avais pas vu votre poste.
      Mlaheureusement, j'ai absolument besoin de le faire en PERL :(
      0
    4. valentin2703 Messages postés 185 Statut Membre 9
       
      Malheureusement pour toi en Perl ça va être plus compliqué ^^
      Voila un bout de code pour t'aider :

      #!/usr/bin/perl   
      use warnings;   
      use strict;   
      
      sub listDirectory {    
       my ($repertoire) = @_;    
       my @fichiers = ();    
       opendir (my $rep_fh, $repertoire) or die "impossible d'ouvrir le repertoire $repertoire\n";    
       my @file_rep = grep { !/^\.\.?$/ } readdir($rep_fh);    
       closedir ($rep_fh);    
       foreach my $nom (@file_rep) {   
        if (-f "$repertoire/$nom") { push (@fichiers, $nom); }    
       }   
       return @fichiers;    
      }   
      
      my $repertoire = "TON DOSSIER"; # Répertoire qui contient tes fichiers   
      my @fichiers = &listDirectory($repertoire);   # Tableau avec tous tes fichiers   
      my $lengthFichiers = scalar @fichiers;    # Taille du tableau   
      
      # TRIER LE TABLEAU SELON TES PARAMETRES   
      
      # Ecrire dans le fichier de sortie   
      my $finalFile = "fichier_concat_final.txt";   
      open(ECRIRE, ">$finalFile") || die ("Erreur d'ouverture de $finalFile");   
      
      for(my $i = 0; $i < $lengthFichiers; $i++) {   
       my $currentFile = $repertoire . "/" . $fichiers[$i];   
       open(LIRE, $currentFile) || die ("Erreur d'ouverture de $currentFile");   
       while(<LIRE>) { print ECRIRE $_; }   
       close(LIRE);   
      }   
      
      close(ECRIRE);


      Et oui le perl c'est pas très esthétique :D
      La partie la plus compliquer va être de trier le tableau selon tes paramètres, voici un lien pour t'aider http://articles.mongueurs.net/magazines/linuxmag48.html
      En espérant que ça t'aide.

      Edit : Je suis sur un système linux, à toi d'adapter le dossier si tu est sur windows
      0
    5. heyquem Messages postés 808 Statut Membre 131
       
      Tant pis pour toi ! :))
      0
  8. Amine7592 Messages postés 28 Statut Membre
     
    J'ai encore une question :)

    Le programme ci-dessus, lit tous les fichiers se trouvant dans "le répertoire". or moi, j'aurai besoin de lire seulement les fichier començant par une chaine de caractères, par exemple : A_2012_*

    Merci pour votre retour.
    0
    1. valentin2703 Messages postés 185 Statut Membre 9
       
      Il faut utiliser les regex pour traiter les fichiers récupérés.
      Par exemple :
      if($fichier =~ m/A_2012_(.*)/) { OK }
      0
    2. valentin2703 Messages postés 185 Statut Membre 9
       
      Voila ce que ça donne dans ton cas :
      sub listDirectory { 
       my ($repertoire) = @_; 
       my @fichiers = (); 
       opendir (my $rep_fh, $repertoire) or die "impossible d'ouvrir le repertoire $repertoire\n"; 
       my @file_rep = grep { !/^\.\.?$/ } readdir($rep_fh); 
       closedir ($rep_fh); 
       foreach my $nom (@file_rep) { 
        if (-f "$repertoire/$nom") {
         # Si le fichier est sous la forme A_2012_*, alors on le prend en compte
         if($nom =~ m/A_2012_(.*)/) { push (@fichiers, $nom); }
        } 
       } 
       return @fichiers; 
      }
      0
    3. Amine7592 Messages postés 28 Statut Membre
       
      @Valentin: Again, MERCI beauacoup pour votre aide.

      Bonne soirée
      0
    4. Amine7592 Messages postés 28 Statut Membre
       
      Bonjour,

      J'ai encore une autre question :
      Comment peut-on tester l'existence des fichiers commençant par "A_2010_*" ?

      J'ai essayé le code ci-dessous, mais malheureusement ça ne marche pas. Pourriez-vous m'aider ?

      Merci à vous !

      if ( -e "A_2010_*")
      {
      }
      0
    5. valentin2703 Messages postés 185 Statut Membre 9
       
      Re-bonjour,

      Pour tester l'éxistance d'un fichier, il faut utiliser la commande if(-f FICHIER).
      Donc si tu veut tester l'éxistance d'un fichier commençant par A_2010_* il faut combiner ton teste avec la regex suivante : my $file =~ m/^A_2010_(.*)/;
      Ce qui te donne :
      if( -f $file) { #FICHIER EXISTE } else { #FICHIER N EXISTE PAS }
      0