1
votes

regex pour tester les caractères séparés par des espaces

Je veux créer une expression régulière qui valide le format d'heure "lisible par l'homme", où il devrait ressembler à ceci:

1 sem 1 j 1h 1 min

et les unités de temps acceptées sont (sensibles à la casse):

  • w pendant des semaines
  • d pour les jours
  • h pendant des heures
  • m pendant quelques minutes

chaque unité de temps est facultative et ne doit exister qu'une seule fois au maximum, les formats suivants doivent donc l'être également (par exemple):

  • 1 sem 1 j
  • 1 sem 1h 1m
  • 1j 1h 1m
  • 1h 1m
  • 1 sem 1 m

et c'est ce que j'ai essayé jusqu'à présent:

/ ((\ dw) (\ dd) (\ dh) (\ dm)) / i

l'expression ci-dessus validera tous les formats de listes, mais elle négligera les espaces entre les unités de temps, je veux rendre l'espace obligatoire entre une unité de temps et une autre.


11 commentaires

Cette regex ne validera pas ces chaînes, elle ne correspondra qu'à la première unité.


Vous pouvez essayer \ d + [wdhml] (?: + \ d + [wdhml]) +


@ WiktorStribiżew ouais désolé, j'ai collé le mauvais


Votre regex rend les espaces obligatoires dans l'entrée. Alors quel est le problème? Les rendre tous facultatifs?


@ WiktorStribiżew, il ne devrait pas y avoir plus d'un espace entre chaque unité de temps


Utilisez l'expression régulière dans mon commentaire précédent et supprimez + après l'espace \ d + [wdhml] (?: \ d + [wdhml]) +


@revo, ça marche bien, merci. mais si je veux faire correspondre des nombres flottants au lieu d'entiers, y a-t-il un raccourci de ceci: (([0-9] * [.])? [0-9] +) + [wdhm] (?: (( [0-9] * [.])? [0-9] +) + [wdhm]) +


Essayez-vous de faire correspondre ou de valider? car si la validation est déjà effectuée, vous pouvez maintenant opter pour une expression régulière plus courte, mais si vous avez besoin des deux en même temps, il faut plus de conditions.


@revo je veux valider


Le regex ultime serait ^ (?!. * ([Wdhml]). * \ 1) \ d * \.? \ D + [wdhml] (?: \ d * \.? \ D + [wdhml]) * $ . Voir la démo en direct ici regex101.com/r/kOUgej/1


@revo merci, c'est l'expression la plus complète


5 Réponses :


0
votes

Essayez celui-ci:

regex = /\b\d[wdhm]{1}\b/ig;
match = '1w 1h 1d'.match(regex);
console.log(match)

\ b correspond à une limite de mot.

Voir le docs


0 commentaires

3
votes

^(\d+w\s?)?(\d+d\s?)?(\d{1,2}h\s?)?(\d{1,2}m)?$
const regex = /^(\d+w\s?)?(\d+d\s?)?(\d{1,2}h\s?)?(\d{1,2}m)?$/

const text = "1w 8d 1h 5m"

console.log(text.match(regex)["input"])

console.log(regex.test(text))


2 commentaires

il correspond à 1w1d


Je sais qu'il correspond également à 1w8d1h5m car l'espace est facultatif



1
votes

console.clear();
dates = [
  // true
  "4w 1m",
  "4w 3d 2h 1m",
  "3d",
  "2h",
  "1m",
  "3d 2h",
  // false
  "4w3d",
  "2h 3d",
  "42",
  "Lorem ipsum",
  "4w 3d 2h 2h",
  "1m 1m"
];


reg = /^\s*(\d{1,2}w\s+)?(\d{1,2}d\s+)?(\d{1,2}h\s+)?(\d{1,2}m\s+)?$/;

dates.forEach(function(item, index, arr) {
  console.log(item, this.test(item))
}, reg)


1 commentaires

1h 1m doit correspondre:> chaque unité de temps est facultative



0
votes

Essayez Regex: ^ (? =. * \ d [wdhm]) (?: \ dw)? (?:? (? <= ^ |) (?: \ dd))? (?: ? (? <= ^ |) (?: \ dh))? (?: (? <= ^ |) (?: \ dm))? $

Démo


1 commentaires

faut-il faire correspondre 1w 1w ?



3
votes

Pour valider ces chaînes, vous avez besoin d'une expression régulière plus complète. L'expression régulière suivante correspond aux deux extrémités de la chaîne d'entrée et garantit que la répétition des lettres ne se produira pas en utilisant une anticipation négative:

^(?:\d*\.?\d+([wdhml])(?!.*\1)(?: (?=.)|$))+$

\ d * \.? \ D + est utilisé pour autoriser les décimales, par exemple 1.5 ou .5 (mais attention, cela n'autorise pas 1.)

Voir démo en direct ici

Une révision plus courte mais moins lisible des regex ci-dessus est (crédits d'une telle le mixage va à @bobblebubble ):

^(?!.*([wdhml]).*\1)\d*\.?\d+[wdhml](?: \d*\.?\d+[wdhml])*$


0 commentaires