Microsoft 365 InStr, c'est bien, mais trop court ! !

DenisHen

XLDnaute Nouveau
Bonjour à la communauté...
Voilà, j'ai un tableau avec des string construit comme :
VB:
Tableau(1)="4/12/4"
Tableau(....)="..."
Tableau(6)="4/18/4"
Tableau(....)="..."
Tableau(33)="44.2/16/44.2"
Tableau(44)="44.2/16/4"
Je cherche donc avec un Do While dans mon tableau, du début à la fin, jusq'à trouvé un InStr <> 0, puis je sors.
Mon problème est que si je cherche "44.2/16/4", InStr le trouve en premier dans "44.2/16/44.2" : Tableau(33), alors que j'aimerais le trouver dans Tableau(44).
Ce qui est normal, mais j'aimerais trouver l'exacte chaine, de la bonne longueur. D'où mon sujet, c'est trop court, ou trop long ! !
J'avais pensé à un Mid, mais je n'y arrive pas...
Il faut savoir aussi que la chaine recherchée sera TOUJOURS de la bonne longueur, et je dois trouver l'exacte réplique, bref, les deux chaines doivent être de la même taille...
Et oui, je parle bien ici de double vitrage... ;)
Si quelqu'un a une astuce, un conseil, voir même la solution... Je suis preneur...
Bien à toi la communauté.
Denis...
 
Dernière édition:

DenisHen

XLDnaute Nouveau
Salut vgendron, et merci pour ta réponce.
Mon problème est que, la chaine recherchée "44.2/16/4" est dans une autre, comme : "...double vitrage type 44.2/16/4 à un seul feuilletage...".
Donc, je cherche dans mon tableau si il est contenu dans ma chaine...
 

TooFatBoy

XLDnaute Barbatruc
Mon problème est que, la chaine recherchée "44.2/16/4" est dans une autre, comme : "...double vitrage type 44.2/16/4 à un seul feuilletage...".

Mais si je cherche "44.2/16/4[espace] " je ne trouverais pas ce que je cherche, si ?
Car je cherche l'exacte réplique...
Tu as dit que "44.2/16/4" était contenu dans la phrase "...double vitrage type 44.2/16/4 à un seul feuilletage...", et dans cette phrase il y a bien une espace après le 4, donc tu devrais trouver la chaîne "44.2/16/4 ". ;)

Mais ma proposition était juste pour avoir un minimum de modification à effectuer pour que ça fonctionne.
La meilleure solution n'est probablement pas celle-là.
 

mapomme

XLDnaute Barbatruc
Supporter XLD
Bonsoir à tous :),
Pas d'énoncé clair, pas de fichier, pas de code, pas de données de départ, pas d'exemple de résultat souhaité. Dans ce cas, une seule méthode a fait ses preuves : La méthode IRMA.
1719437205250.png
 

mapomme

XLDnaute Barbatruc
Supporter XLD
Re,
Après avoir dialogué avec un collègue recommandé par Mme Irma et fait chauffer la carte bleue, voilà la réponse du grand mage :
VB:
Dim valeur, tableau(1 To 50), i&, j&, n&, s
   tableau(1) = "4/12/4"
   tableau(6) = " toto 4/18/4 titi tata"
   tableau(33) = "44.2/16/44.2"
   tableau(44) = "...double vitrage type 44.2/16/4 à un seul feuilletage..."
 
   valeur = "44.2/16/44"
 
   For i = 1 To UBound(tableau)
      n = 0: s = Split(tableau(i))
      For j = 0 To UBound(s)
         If valeur = s(j) Then n = i: Exit For
      Next
      If n > 0 Then Exit For
   Next i
   If n = 0 Then
      MsgBox " la valeur " & valeur & " n'a pas été trouvée !", vbExclamation
   Else
      MsgBox " la valeur " & valeur & " a été trouvée  dans tableau(" & n & ") :" & vbLf & _
         tableau(n), vbInformation
   End If

[HUMOUR]
1719439284201.png
[/HUMOUR]
 

klin89

XLDnaute Accro
Bonsoir à tous, :)

Peut-être avec un Regex, mais bon je ne suis pas un spécialiste :rolleyes:
VB:
Sub test()
    Dim r As Range, chaine, m As Object
    chaine = "44.2/16/4"
    With CreateObject("VBScript.RegExp")
        .Global = True
        .Pattern = "\b(" & chaine & ")\b"
        For Each r In Selection
            For Each m In .Execute(r)
                r.Characters(m.firstindex + 1, m.Length).Font.Bold = True
            Next
        Next
    End With
End Sub
A tester sur ta plage sélectionnée.
klin89
 

jurassic pork

XLDnaute Junior
Hello,
Klin89, déjà DenisHen demande du code pour un tableau et pas pour une plage de cellules et ensuite tes \b (word boundary) ne fonctionneront pas dans tout les cas de figures car cela prend en considération les mots constitués de caractères alphanumériques et le _ . En particulier les / et . ne sont pas pris en compte.
Je propose le motif suivant :
VB:
.Pattern = "(\s|^)(" & valeur & ")(\s|$)"
c'est à dire un mot qui commence après un espace ou le début de ligne et se termine avant un espace ou la fin de ligne.
Exemple :
Code:
Sub TestFindStrRegex()
Dim valeur, tableau(1 To 50), i&, j&, n&, s, res
   tableau(1) = "4/12/4"
   tableau(6) = " toto 4/18/4 titi tata"
   tableau(33) = "44.2/16/44.2"
   tableau(35) = "...vitrage type 44.2/16/44"
   tableau(44) = "...double vitrage type 44.2/16/4 à un seul feuilletage..."
   valeur = "44.2/16/44"
   res = ""
   With CreateObject("VBScript.RegExp")
      '.Pattern = "\b(" & valeur & ")\b"
      .Pattern = "(^|\s)(" & valeur & ")(\s|$)"
   For i = 1 To UBound(tableau)
       If .Test(tableau(i)) Then res = res + CStr(i) + " "
   Next i
   End With
   If res <> "" Then
      MsgBox "Valeur présente en position(s) : " + res, vbExclamation
   Else
      MsgBox "Valeur pas trouvée" , vbExclamation
   End If
End Sub

Avec mon motif, seule la valeur du tableau d'indice 35 est trouvée. Avec le motif .Pattern = "\b(" & valeur & ")\b les valeurs du tableau d'indices 33 et 35 sont trouvées.

Ami calmant, J.P
 

DenisHen

XLDnaute Nouveau
Bonjour à toutes et à tous.
J'ai fini par avoir une réponse (ailleurs), mais je n'avais accès qu'à elles aujourd'hui.
Un super grand merci à vous, je poste la réponse pour plusieurs raisons, dont chacune est suffisante seule (Merci Edmond) :
VB:
i = 1
Do While i <= UBound(tableau)
    If tableau(i) = searchString Then
        foundIndex = i
        Exit Do
    End If
    i = i + 1
Loop
 
If foundIndex <> -1 Then
    MsgBox "Chaîne trouvée à l'index " & foundIndex
Else
    MsgBox "Chaîne non trouvée"
End If
Encore un grand merci pour votre aide ! ! !
@mapomme : je n'ai pas pigé le "split", mais je vais chercher...
@jurassic pork et @klin89 : merci pour "CreateObject("VBScript.RegExp")", mais j'essai d'arrêter...
@Dranreb : Je n'ai rien compris, mais justement, je vais chercher ce "like", car ça me parrais puissant ! !
En tous cas, encore mille mercis à vous...
Denis...
 

jurassic pork

XLDnaute Junior
J'ai fini par avoir une réponse (ailleurs), mais je n'avais accès qu'à elles aujourd'hui.
Un super grand merci à vous, je poste la réponse pour plusieurs raisons, dont chacune est suffisante seule (Merci
Hello,
Le souci avec cette solution c'est que cela ne fonctionne pas si la chaîne dans laquelle on cherche contient plus de caractères que la chaîne recherchée. Exemple :
VB:
Sub TrouveChaine()
Dim valeur, tableau(1 To 50), i&, res, foundIndex&
   tableau(1) = "4/12/4"
   tableau(6) = " toto 4/18/4 titi tata"
   tableau(33) = "44.2/16/44.2"
   tableau(35) = "...vitrage type 44.2/16/44"
   tableau(44) = "...double vitrage type 44.2/16/4 à un seul feuilletage..."
   searchString = "44.2/16/44"
i = 1
foundIndex = -1
Do While i <= UBound(tableau)
    If tableau(i) = searchString Then
        foundIndex = i
        Exit Do
    End If
    i = i + 1
Loop
 
If foundIndex <> -1 Then
    MsgBox "Chaîne trouvée à l'index " & foundIndex
Else
    MsgBox "Chaîne non trouvée"
End If


End Sub
rien n'est trouvé alors qu'il devrait y a avoir la valeur du tableau d'indice 35.
La solution de Dranreb avec le Like est la plus simple et la plus sûre :
Code:
Sub TestFindStrLike()
Dim valeur, tableau(1 To 50), i&, res
   tableau(1) = "4/12/4"
   tableau(6) = " toto 4/18/4  titi tata"
   tableau(33) = "44.2/16/44.2"
   tableau(35) = "...vitrage type   44.2/16/44  "
   tableau(44) = "...double vitrage type 44.2/16/4 à un seul feuilletage..."
   valeur = "44.2/16/44"
   res = ""
      For i = 1 To UBound(tableau)
        If ContientMot(tableau(i), valeur) Then res = res + CStr(i) + " "
      Next i
   If res <> "" Then
      MsgBox "Valeur présente en position(s) : " + res, vbExclamation
   Else
      MsgBox "Valeur pas trouvée" + res, vbExclamation
   End If
End Sub


Function ContientMot(ByVal Phrase As String, ByVal Mot As String) As Boolean
   ContientMot = " " & Phrase & " " Like "* " & Mot & " *"
End Function

Ami calmant, J.P
 
Dernière édition:

DenisHen

XLDnaute Nouveau
Bonjour à la communauté.
Un grand merci à vous pour vos réponses.
@Dranreb et @jurassic pork : j'ai bien pris note de la fiabilité et de la simplicité du code de @Dranreb.
Mais j'ai essayé de le "modifier" pour qu'il soit plus "compréhensible" pour moi, dans l'avenir.
J'ai donc écris ça, mais ça ne marche pas :
VB:
Function ChercheVitrage(CalTxt As Range)
  ChercheVitrage = 0
  TextSrc = Replace(CalTxt.Value, ",", ".") 'Car avec Excel, le "point" du pavé numérique peu être une virgule
  TextSrc = Replace(CalTxt.Value, " ", "")  'Car des collègues saisissent parfois "44.2 / 16 / 44.2"
  Lign = 2
  Do While Worksheets("Prix").Cells(Lign, 12).Value <> 0 'Feuille contenant les prix des vitrages
    If ContientMot(TextSrc, Worksheets("Prix").Cells(Lign, 12).Value) Then 'Colonne 12 contatent la valeur du vitrage
      ChercheVitrage = Val(Worksheets("Prix").Cells(Lign, 13).Value) 'Colonne 13 contenant le prix de ce vitrage
      Exit Function
    End If
    Lign = Lign + 1
  Loop
End Function
Function ContientMot(ByVal Phrase As String, ByVal Mot As String) As Boolean
   ContientMot = " " & Phrase & " " Like "* " & Mot & " *"
End Function
Sachant que CalTxt est une adresse contenant : "Double vitrages, face extérieure feuillet 44.6/16/44.2é à retardateur d'effraction SP510 (classe P5A de la norme EN 356), 16 mm de gaz Argon et …."
Et que Worksheets("Prix").Cells(Lign, 12).Value contient la liste des vitrages, telle que :
44.2/16/4
44.2/16/44.2
44.6/16/4
44.6/16/44.2
66.8/16/4
Et la colonne suivante contient les prix...
Quelqu'un pourrait m'expliquer ce que j'ai mal fais ?
Bien à toi la communauté.
Denis...
 

Discussions similaires

Statistiques des forums

Discussions
313 030
Messages
2 094 571
Membres
106 054
dernier inscrit
Mohajer