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 :

recherche dans un dossier


Sujet :

C

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Membre averti
    Homme Profil pro
    Ingénieur c++ junior
    Inscrit en
    Mai 2013
    Messages
    35
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 33
    Localisation : France, Gironde (Aquitaine)

    Informations professionnelles :
    Activité : Ingénieur c++ junior
    Secteur : Santé

    Informations forums :
    Inscription : Mai 2013
    Messages : 35
    Par défaut recherche dans un dossier
    Bonjour

    Je voudrais réaliser un programme en c qui me permet de rechercher tous les fichiers qui suivent le motif d'une expression régulière dans un dossier et tous ses sous-dossier je les stocke ensuite leur nom et chemin dans une liste.
    j'utilise la librairie regex.h pour utiliser les expressions régulières et dirent.h pour naviguer dans les dossier.
    Le debugage au printf m'a permit de voir que l'erreur se trouve dans ma fonction parcours_directory. Voici mon code
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    #include <stdio.h>
    #include <stdlib.h>
    #include <regex.h>
    #include <dirent.h>
    #include "projet.h"
    #include <link.h>
    #include <string.h>
     
     
    int isDir(struct dirent* currentFile)
    {
        if ((strchr(currentFile->d_name, '.')) == NULL) /* Si le nom du fichier n'a pas de point (une extension). */
            return 1;
        else
            return 0;
    }
     
    char* concatpath(char *s1,char *s2)
    	{
         char *s3=NULL;
         s3=(char *)malloc((strlen(s1)+strlen(s2))*sizeof(char));
         strcpy(s3,s1);
    	 strcat(s3,"\\");
         strcat(s3,s2);
         return s3;
    	}
     
     
    int parcours_directory (DIR* rep, regex_t exp, char* path, struct link* l )
    {	int cpt = 0; //compteur pour debugger
    	struct dirent* currentFile;
    	int match;
    	while ((currentFile = readdir(rep)) != NULL)
    		{
    		++cpt;
    		printf("toto parcours 1\n %d\n", cpt);
    		if (isDir(currentFile))
    			{
    			printf("toto parcours 2\n %d\n", cpt);
    			path=concatpath(path, currentFile->d_name); // on met à jour le path
    			rep = opendir(path);
    			parcours_directory(rep, exp, path, l);
    			closedir(rep);
    			}
    		if ((match = regexec (&exp, currentFile->d_name,0, NULL, 0)) == 1)
    			{
    			struct lelement* e;
    			printf("toto parcours 3\n %d\n", cpt);
    			e = create_lelement(currentFile->d_name, path);
    			lnk__add_head(l,e); // on stock dans la  link
    			display_lnk(l);
    			}
    		}
    	return 0;	
    }
     
    int main (int argc, char *argv[]) // argument 1 = chemin racine, argument 2 = expression régulière à chercher
    {
     
        DIR* rep;
        regex_t exp;
        const char* str_regex = argv[2];
        char* path = argv[1];
        struct link* l = lnk__empty();
    	printf("%d", argc);
        if (argc != 3)
        {
                printf(" les arguments doivent etre valides : argument 1 = chemin racin, argument = expression reguliere a chercher.");
                    return 0;
        }
     
    	rep = opendir(path);
    	printf("toto\n");
    	regcomp (&exp, str_regex, REG_NOSUB | REG_EXTENDED); // compilation de l'expression régulière
    	parcours_directory(rep, exp, path, l);
    	printf("tot1");
    	display_lnk(l);
    	regfree (&exp);
    	lnk_free(l);
    	free(path);
        return 0;
    }
    voici mon tad de liste, c'est peu être qui pose problème, mais je ne pense pas.
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    #include "link.h"
     
     
     
     
    struct lelement *create_lelement( char* name, char* path)
    {
    	struct lelement* e = malloc (sizeof(struct lelement));
    	e->name = name;
    	e->path = path;
    	e->next = NULL;
            return e;
    }
     
    struct link* lnk__empty()
    {
    	struct link* l = malloc (sizeof(struct link));
    	l->head = NULL;
    	return l; 
    }
     
     
    int lnk__is_end_mark(struct lelement *e)
    {
      return (e == NULL);
    }
     
    void lnk__add_head(struct link *l, struct lelement *e)
    {
      e->next = l->head;
      l->head = e;
    }
     
    struct lelement *lnk__remove_head(struct link *l)
    {
      struct lelement *tmp = l->head;
      l->head = l->head->next;
      return tmp;
    }
     
     
    void display_lnk (struct link* l)
    {
    	struct lelement *tmp;
    	for(tmp = l->head; !lnk__is_end_mark(tmp->next); tmp = tmp->next)
    	{
    		printf("%s à pour chemin %s\n", tmp->name, tmp->path);
    	}
    } 
     
    void lnk_free(struct link* l)
    {
            struct lelement* tmp;
    	for(tmp = l->head; !lnk__is_end_mark(tmp->next); tmp = tmp->next)
    		free(tmp);
    	free(l);
    }

    Merci pour votre futur aide
    Amicalement Psykomusic.

  2. #2
    Expert éminent
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 398
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 41
    Localisation : France

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 398
    Par défaut
    Attention à l'aliasing! Tous tes éléments seront créés avec le même buffer path...

    Sans compter que tu pointes directement sur le chemin de fichier de la structure dirent, dont tu ne contrôles même pas la durée de vie!
    SVP, pas de questions techniques par MP. Surtout si je ne vous ai jamais parlé avant.

    "Aw, come on, who would be so stupid as to insert a cast to make an error go away without actually fixing the error?"
    Apparently everyone.
    -- Raymond Chen.
    Traduction obligatoire: "Oh, voyons, qui serait assez stupide pour mettre un cast pour faire disparaitre un message d'erreur sans vraiment corriger l'erreur?" - Apparemment, tout le monde. -- Raymond Chen.

  3. #3
    Membre averti
    Homme Profil pro
    Ingénieur c++ junior
    Inscrit en
    Mai 2013
    Messages
    35
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 33
    Localisation : France, Gironde (Aquitaine)

    Informations professionnelles :
    Activité : Ingénieur c++ junior
    Secteur : Santé

    Informations forums :
    Inscription : Mai 2013
    Messages : 35
    Par défaut
    C'est la première fois que j'utilise les biblios dirent et regex et je n'ai pas compris ta réponse ^^

  4. #4
    Expert éminent
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 398
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 41
    Localisation : France

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 398
    Par défaut
    Cette ligne:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    e = create_lelement(currentFile->d_name, path);
    La fonction create_lelement() ne copie pas le buffer: Elle mémorise seulement le pointeur d_name, sur lequel tu n'as pas de contrôle.
    SVP, pas de questions techniques par MP. Surtout si je ne vous ai jamais parlé avant.

    "Aw, come on, who would be so stupid as to insert a cast to make an error go away without actually fixing the error?"
    Apparently everyone.
    -- Raymond Chen.
    Traduction obligatoire: "Oh, voyons, qui serait assez stupide pour mettre un cast pour faire disparaitre un message d'erreur sans vraiment corriger l'erreur?" - Apparemment, tout le monde. -- Raymond Chen.

  5. #5
    Membre averti
    Homme Profil pro
    Ingénieur c++ junior
    Inscrit en
    Mai 2013
    Messages
    35
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 33
    Localisation : France, Gironde (Aquitaine)

    Informations professionnelles :
    Activité : Ingénieur c++ junior
    Secteur : Santé

    Informations forums :
    Inscription : Mai 2013
    Messages : 35
    Par défaut
    yep, je vais passer par une variable intermédiaire afin de ne pas filer le pointeur à mon élément, mais bien la chaine de caractère.

  6. #6
    Membre éclairé
    Homme Profil pro
    amateur
    Inscrit en
    Octobre 2007
    Messages
    731
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Belgique

    Informations professionnelles :
    Activité : amateur

    Informations forums :
    Inscription : Octobre 2007
    Messages : 731
    Par défaut
    Pour ma part, j'utilise dirent de la façon suivante pour effectuer une recherche réursive d'un fichier depuis un répertoire racine.
    Je me contente de matcher un nom, pas de pattern. La où je fais le contrôle du nom du fichier(surligné en rouge), cela pourrait être ton regex.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    char *directory_search_entity(char *directory_path, char *entity_name)
    {
        DIR *directory = NULL;
        char *entity_path = NULL;
        if ( !(entity_path = directory_search_entity_recursive(directory, directory_path, entity_name)) )
            fprintf(logger,"\ndir.h::directory_search_entity -> The %s file has not been found in the %s directory", entity_name, entity_path);
    
        return entity_path;
    }
    
    char *directory_search_entity_recursive(DIR *directory, char *directory_path, char *entity_name)
    {
        directory = directory_open(directory_path);
        struct dirent *entity=NULL;
        seekdir(directory,2);
        char *entity_path = NULL;
        while((entity=readdir(directory)))
        {
            entity_path = get_entity_path(directory_path, entity->d_name);
            if (is_directory(entity_path))
                directory_search_entity_recursive(directory, entity_path, entity_name);
    
            else
            {
                if (strcmp( entity->d_name, entity_name )==0)                
                            while((entity=readdir(directory)));
    
                else deallocate_1D_c(entity_path);
            }
        }
        directory_close(directory);
        return entity_path;
    }

Discussions similaires

  1. recherche dans un dossier
    Par champenois51 dans le forum Word
    Réponses: 1
    Dernier message: 29/12/2013, 18h05
  2. [AppleScript] Rechercher dans un dossier du Finder
    Par iLandes dans le forum AppleScript
    Réponses: 1
    Dernier message: 17/01/2011, 20h29
  3. Réponses: 0
    Dernier message: 17/05/2010, 10h43
  4. [BATCH] Recherche dans sous-dossiers
    Par tonf dans le forum Scripts/Batch
    Réponses: 9
    Dernier message: 13/08/2008, 15h17
  5. Recherche d'un dossier dans le disque
    Par com-ace dans le forum Access
    Réponses: 6
    Dernier message: 31/08/2006, 10h51

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