XL 2010 extraction d'une partie de nom de fichier

herve62

XLDnaute Barbatruc
Bonsoir
Quel serait pour vous le code le plus simple pour récupérer en vba une partie de nom de fichier
j'ai x fichiers dont le nom est
Jeux Liste 1 - 20.xlsx
Jeux Liste 21 - 40.xlsx
Jeux Liste 41 - 60.xlsx
.....
Jeux Liste 121 - 140.xlsx

Il me faudrait récupérer en temps que string la partie par exemple "1 - 20" ; "41 - 60" , "121 - 140" ..etc
Vu que c'est variable en longueur entre 6 et 9 .. ??? avec les espaces plus les digits de 1 à 3
Vous me direz on peut retirer les espaces .. Oui , mais pas les digits !!
je pense que cela ira plus vite avec vos avis
merci
 

patricktoulon

XLDnaute Barbatruc
Bonsoir
il y a 36 façons d'y arriver en vba
VB:
Function Extract_Donnees$(ByVal Nom_Fichier$)
    Dim Compteur%, t$
    For Compteur = 1 To Len(Nom_Fichier)
        If IsNumeric(Mid(Nom_Fichier, Compteur, 1)) Then t = Mid$(Nom_Fichier, Compteur): Exit For
    Next Compteur
    Extract_Donnees = Left(t, Len(t) - (Len(t) - InStrRev(t, ".") + 1))
End Function

ou bien
VB:
Function Extract_Donnees$(ByVal Nom_Fichier$)
    Dim Compteur%, t$
    t = Nom_Fichier
    For Compteur = 1 To Len(Nom_Fichier)
        If Not (Mid(t, Compteur, 1)) Like "[0-9|-]" Then Mid(t, Compteur, 1) = " "
    Next Compteur
    Extract_Donnees = Trim(t)
End Function

et pour reprendre l'exemple de @Yeahou a savoir ne faire que 9 tours de boucle maxi (1 to 9)
on simplifie l’après boucle
VB:
Function Extract_Donnees$(ByVal Nom_Fichier$)
    Dim Compteur%, t$, debut&, x&
    t = Nom_Fichier:   debut = Len(t)
     For Compteur = 0 To 9
        x = InStr(1, t, Compteur): If x < debut And x > 0 Then debut = x
        Next Compteur
    Extract_Donnees = Left(Mid$(t, debut), InStr(1, Mid$(t, debut), ".") - 1)
End Function
 
Dernière édition:

mapomme

XLDnaute Barbatruc
Supporter XLD
Bonsoir Luc , ta fonction tu la met OU ?? je suis en VBA PUR !
Re,

La fonction est à mettre dans un module de ton projet pas dans un module rattaché à une feuille (ni rattaché au module de ThisWorkbook).

Ensuite, on peut l'utiliser soit au sein d'une feuille de calcul soit dans du code VBA.

Voir fichier joint. Le code est dans module1.
 

Pièces jointes

  • herve62- extraction- v1.xlsm
    18.7 KB · Affichages: 0
Bonjour le fil

et pour reprendre l'exemple de @Yeahou a savoir ne faire que 9 tours de boucle maxi (1 to 9)
on simplifie l’après boucle
Extract_Donnees = Left(Mid$(t, debut), InStr(1, Mid$(t, debut), ".") - 1)
Extract_Donnees = Mid$(Nom_Fichier, Compteur, InStr(Compteur, Nom_Fichier, ".") - Compteur)
Salut Patrick ;), tu simplifies quoi ? 🥴
tu fais un left et un mid de plus, explique moi l'astuce ! 🤔

Bien amicalement, @+
 

patricktoulon

XLDnaute Barbatruc
Bonjour @Yeahou;)

VB:
Function Extract_Donnees$(ByVal Nom_Fichier$)
Dim Compteur%, Compteur2 As Byte
Compteur = Len(Nom_Fichier)
For Compteur2 = 0 To 9
    ' calcul l'index de debut de la chaine numerique avec instr +app.min + 2d instr
    If InStr(1, Nom_Fichier, Compteur2) Then Compteur = Application.Min(Compteur, InStr(1, Nom_Fichier, Compteur2))
Next Compteur2
 'restitution de  la chaine avec mid et les index debut et fin par le instr "." +calcul - compteur
  Extract_Donnees = Mid$(Nom_Fichier, Compteur, InStr(Compteur, Nom_Fichier, ".") - Compteur)
End Function


Function Extract_Donnees$(ByVal Nom_Fichier$)
    Dim Compteur%, t$, debut&, x&
    t = Nom_Fichier:   debut = Len(t)
     For Compteur = 0 To 9
         ' calcul l'index de debut de la chaine numerique avec instr  tout court
  x = InStr(1, t, Compteur): If x < debut And x > 0 Then debut = x
        Next Compteur
    'restitution de  la chaine avec le left du mid et les index debut et fin par le instr "."
    Extract_Donnees = Left(Mid$(t, debut), InStr(1, Mid$(t, debut), ".") - 1)
End Function
1° ma ligne de calcul debut est donc moins lourde car app.min est plus lourd qu'un test "< que"
et tu utilise deux fois le calculateur avec instr dans ta ligne de calcul(1 fois pour le instr de i et une fois pour le app.min)

2° ma ligne de restitution ne recalcule pas le instr "." - compteur
j'utilise le left de la chaîne a partir de l'index début et non la chaîne entière par le mid
il est vrai que si on voulais parfaire et éviter les double calculs on devrait variabiliser
En l’occurrence ici on réutilise la variable "t"
COMME SUIT
VB:
Function Extract_Donnees$(ByVal Nom_Fichier$)
    Dim Compteur%, t$, debut&, x&, Res$
    t = Nom_Fichier:   debut = Len(t)
     For Compteur = 0 To 9
         ' calcul l'index de debut de la chaine numerique avec instr  tout court
  x = InStr(1, t, Compteur): If x < debut And x > 0 Then debut = x
        Next Compteur
     t = Mid$(t, debut):Extract_Donnees = Mid$(t, 1, InStr(1, t, ".") - 1)
End Function

de même que pour encore plus alléger on pourrait ne pas allouer de mémoire supplémentaire avec "T" et utiliser nom_fichier qui est déjà alloué en mémoire (comme tu le fait )
comme suit (j'ai raccourci le nom de l'argument)
VB:
Function Extract_Donnees$(ByVal NF$)
    Dim Compteur%,  debut&, x&
       debut = Len(NF)
     For Compteur = 0 To 9
    x = InStr(1, NF, Compteur): If x < debut And x > 0 Then debut = x
        Next Compteur
     NF = Mid$(NF, debut): Extract_Donnees = Mid$(NF, 1, InStr(1, NF, ".") - 1)
End Function

si je devais merger nos deux ecritures ce serait serait alors comme suit
VB:
Function Extract_Donnees$(ByVal NF)
    Dim Compteur%, t$, debut&, x&, Res$
       debut = Len(NF)
     For Compteur = 0 To 9
    x = InStr(1, NF, Compteur): If x < debut And x > 0 Then debut = x
        Next Compteur
      Extract_Donnees = Mid$(NF, debut, InStr(1, NF, ".") - debut)
End Function

il est vrai que la boucle sur le instr 0-9 sera plus performante sur des chaînes plus longues car !!! maxi on boucle 9 fois

sur des chaines ou le premier chiffre est placé a moins de 9 caractères avec 9 comme premier caractère numérique elle serait alors moins véloce que q'une boucle sur le len

c'est un choix cornélien 😂🤣😅😇



l’économie est là me semble til
tu test if instr pour zapper le zéro(non trouvé) + un re test avec instr(le meme test) + app.min
alors q'il est moins lourd (me semble t il de tester if x>0
VB:
  If InStr(1, Nom_Fichier, Compteur2) Then Compteur = Application.Min(Compteur, InStr(1, Nom_Fichier,

ici je fait qu'un seul test instr et je test un numérique > 0 et < que le debut
VB:
  x = InStr(1, NF, Compteur): If x < debut And x > 0 Then debut = x
nous savons très bien tout les deux que le plus gourmand en VBA c'est bien le travail sur des chaînes en string ;)

mon écriture est aussi plus accessible a un novice je pense

a tester sur beaucoup de ligne
 

herve62

XLDnaute Barbatruc
Bonjour
Merci bien à tous , hier soir un peu fatigué j'ai pas tout testé
Je viens de reprendre , en fait cela fonctionne depuis le #7
Finalement j'ai opté pour un des derniers de Patrick que j'essaie de comprendre ( le principe)
Question : pourquoi les $ en fin de variable même dans celui de Function ?
 
Re,

Question : pourquoi les $ en fin de variable même dans celui de Function ?
pour obliger une chaine texte, non un variant, en retour de fonction, c'est pareil que
Function Extract_Donnees(ByVal Nom_Fichier as String) as String
Comme tu as besoin d'une chaine texte et que tes valeurs sont numériques avec opérateur - (ex: 1 - 20), c'est plus propre et sûr

Bien cordialement, @+
 

Discussions similaires

Haut Bas