Question

J'essaie d'analyser une chaîne comme celle-ci à l'aide d'une expression régulière .NET :

H3Y5NC8E-TGA5B6SB-2NVAQ4E0

et renvoyez ce qui suit en utilisant Split :H3Y5NC8E TGA5B6SB 2NVAQ4E0

Je valide chaque caractère par rapport à un jeu de caractères spécifique (notez que les lettres « I », « O », « U » et « W » sont absentes), donc utiliser string.Split n'est pas une option.Le nombre de personnages dans chaque groupe peut varier et le nombre de groupes peut également varier.J'utilise l'expression suivante :

([ABCDEFGHJKLMNPQRSTVXYZ0123456789]{8}-?){3}

Cela correspondra exactement à 3 groupes de 8 caractères chacun.Plus ou moins fera échouer le match.Cela fonctionne dans la mesure où cela correspond correctement à l’entrée.Cependant, lorsque j'utilise la méthode Split pour extraire chaque groupe de caractères, j'obtiens simplement le groupe final.RegexBuddy se plaint que j'ai répété le groupe de capture lui-même et que je devrais mettre un groupe de capture autour du groupe répété.Cependant, aucune de mes tentatives dans ce sens n’aboutit au résultat souhaité.J'ai essayé des expressions comme celle-ci :

(([ABCDEFGHJKLMNPQRSTVXYZ0123456789]{8})-?){4}

Mais cela ne fonctionne pas.

Puisque je génère l'expression régulière dans le code, je pourrais simplement l'étendre en fonction du nombre de groupes, mais j'espérais une solution plus élégante.


Veuillez noter que le jeu de caractères n'inclut pas l'intégralité de l'alphabet.Il fait partie d'un système d'activation de produit.Ainsi, tous les caractères pouvant être accidentellement interprétés comme des chiffres ou d’autres caractères sont supprimés.par exemple.Les lettres « I », « O », « U » et « W » ne font pas partie du jeu de caractères.

Les traits d'union sont facultatifs puisqu'un utilisateur n'a pas besoin de les saisir, mais ils peuvent être là si l'utilisateur a effectué un copier-coller.

Était-ce utile?

La solution 2

J'ai découvert la réponse que je recherchais.Voici mon code de travail :

    static void Main(string[] args)
    {
        string pattern = @"^\s*((?<group>[ABCDEFGHJKLMNPQRSTVXYZ0123456789]{8})-?){3}\s*$";
        string input = "H3Y5NC8E-TGA5B6SB-2NVAQ4E0";
        Regex re = new Regex(pattern);
        Match m = re.Match(input);

        if (m.Success)
            foreach (Capture c in m.Groups["group"].Captures)
                Console.WriteLine(c.Value);
    }

Autres conseils

BTW, vous pouvez remplacer la classe de caractères [ABCDEFGHJKLMNPQRSTVXYZ0123456789] par une classe de caractères soustraits plus lisible.

[[A-Z\d]-[IOUW]]

Si vous voulez juste faire correspondre 3 groupes comme celui-là, pourquoi n'utilisez-vous pas ce modèle 3 fois dans votre regex et utilisez simplement 1, 2, 3 sous-groupes capturés pour former la nouvelle chaîne ?

([[A-Z\d]-[IOUW]]){8}-([[A-Z\d]-[IOUW]]){8}-([[A-Z\d]-[IOUW]]){8}

En PHP je reviendrais (je ne connais pas .NET)

return "$1 $2 $3";

Après avoir examiné votre question et les réponses données, j'ai trouvé ceci :

RegexOptions options = RegexOptions.None;
Regex regex = new Regex(@"([ABCDEFGHJKLMNPQRSTVXYZ0123456789]{8})", options);
string input = @"H3Y5NC8E-TGA5B6SB-2NVAQ4E0";

MatchCollection matches = regex.Matches(input);
for (int i = 0; i != matches.Count; ++i)
{
    string match = matches[i].Value;
}

Puisque le "-" est facultatif, vous n'avez pas besoin de l'inclure.Je ne sais pas pourquoi vous utilisiez le {4} à la fin ?Cela trouvera les correspondances en fonction de ce que vous voulez, puis en utilisant MatchCollection, vous pourrez accéder à chaque correspondance pour reconstruire la chaîne.

Pourquoi utiliser Regex ?Si les groupes sont toujours divisés par un -, ne pouvez-vous pas utiliser Split() ?

Désolé si ce n'est pas ce que vous vouliez, mais votre chaîne a toujours un trait d'union séparant les groupes, alors au lieu d'utiliser regex, ne pourriez-vous pas utiliser la méthode String.Split() ?

Dim stringArray As Array = someString.Split("-")

Quelles sont les caractéristiques déterminantes d’un bloc valide ?Nous aurions besoin de le savoir pour être vraiment utiles.

Ma suggestion générique, validez le jeu de caractères dans un premier temps, puis divisez et analysez dans une méthode distincte en fonction de ce que vous attendez.S'il s'agit d'un site Web/d'une application, vous pouvez utiliser la validation ASP Regex sur le front-end, puis la diviser sur le back-end.

Si vous vérifiez simplement la valeur du groupe, avec group(i).value, alors vous n'obtiendrez que la dernière.Cependant, si vous souhaitez énumérer toutes les fois où ce groupe a été capturé, utilisez group(2).captures(i).value, comme indiqué ci-dessous.

system.text.RegularExpressions.Regex.Match("H3Y5NC8E-TGA5B6SB-2NVAQ4E0","(([ABCDEFGHJKLMNPQRSTVXYZ0123456789]+)-?)*").Groups(2).Captures(i).Value

Mike,

Vous pouvez utiliser le jeu de caractères de votre choix dans le groupe de caractères.Tout ce dont vous avez besoin est d'ajouter le modificateur "+" pour capturer tous les groupes.Voir ma réponse précédente, remplacez simplement [A-Z0-9] par ce dont vous avez besoin (c'est-à-dire[ABCDEFGHJKLMNPQRSTVXYZ0123456789])

Vous pouvez utiliser ce modèle :

Regex.Split("H3Y5NC8E-TGA5B6SB-2NVAQ4E0", "([ABCDEFGHJKLMNPQRSTVXYZ0123456789]{8}+)-?")

Mais vous devrez filtrer les chaînes vides du tableau résultant.Citation de MSDN:

Si plusieurs correspondances sont adjacentes les unes aux autres, une chaîne vide est insérée dans le tableau.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top