Faire correspondre un espace dans une expression régulière

229

J'ai besoin de faire correspondre un caractère espace dans une expression régulière PHP. Quelqu'un a une idée?

Je veux dire comme "gavin schulz", l'espace entre les deux mots. J'utilise une expression régulière pour m'assurer que je n'autorise que des lettres, des chiffres et un espace. Mais je ne sais pas comment trouver l'espace. Voici ce que j'ai en ce moment:

$newtag = preg_replace("/[^a-zA-Z0-9s|]/", "", $tag);
Gavin Schulz
la source
2
Hmm ... il n'est pas question non plus de faire correspondre un 'a' ou un 'b' ...;)
1
vous devriez voir les exemples d'
expressions régulières

Réponses:

368

Si vous cherchez un espace, ce serait " "(un espace).

Si vous cherchez un ou plusieurs, c'est " *"(c'est deux espaces et un astérisque) ou " +"(un espace et un plus).

Si vous recherchez un espacement commun, utilisez "[ X]"ou "[ X][ X]*"ou "[ X]+"où se Xtrouve le caractère de tabulation physique (et chacun est précédé d'un seul espace dans tous ces exemples).

Ceux-ci fonctionneront dans tous les moteurs * regex que j'ai jamais vus (dont certains n'ont même pas le caractère un ou plusieurs "+", ugh).

Si vous savez que vous utiliserez l'un des moteurs regex les plus modernes, "\s"et ses variations sont la voie à suivre. En outre, je crois que les limites des mots correspondent également au début et à la fin des lignes, ce qui est important lorsque vous recherchez des mots qui peuvent apparaître sans espaces précédant ou suivant.

Pour PHP en particulier, cette page peut vous aider.

De votre édition, il semble que vous souhaitiez supprimer tous les caractères non valides Le début de ceci est (notez l'espace à l'intérieur de l'expression régulière):

$newtag = preg_replace ("/[^a-zA-Z0-9 ]/", "", $tag);
#                                    ^ space here

Si vous voulez également que la ruse garantisse qu'il n'y ait qu'un seul espace entre chaque mot et aucun au début ou à la fin, c'est un peu plus compliqué (et probablement une autre question) mais l'idée de base serait:

$newtag = preg_replace ("/ +/", " ", $tag); # convert all multispaces to space
$newtag = preg_replace ("/^ /", "", $tag);  # remove space from start
$newtag = preg_replace ("/ $/", "", $tag);  # and end
paxdiablo
la source
Son expression originale semblait vouloir remplacer le caractère "". Vous annulez l'espace, donc son espace ne sera pas "supprimé" comme prévu.
Suroot
Citant: "n'autoriser que les lettres, les chiffres et un espace", l'ER original de Gavin était faux (c'est pourquoi il posait la question). Mon RE supprime tout ce qui n'en fait pas partie.
paxdiablo
Pourquoi l'espace doit-il se trouver à la fin du modèle de correspondance plutôt qu'au milieu, par exemple?
warren
1
@warren, ce n'est pas le cas. Le commentaire «l'espace ici» ne disait pas allait cet espace, mais plutôt qu'il y avait un espace là-bas (au cas où le lecteur ne s'en serait pas rendu compte).
paxdiablo
@ Mike, non, ce n'est pas le cas. Le but ici est de remplacer tous les caractères qui ne sont pas dans l'ensemble A-Za-z.... Le curseur entre crochets le dicte. Le déplacement du curseur en dehors des crochets change sa signification en caractères correspondants dans l'ensemble au début de la chaîne.
paxdiablo
34

Voici tout ce que vous devez savoir sur les espaces dans les expressions régulières:

  • [[:blank:]] Espace ou tabulation uniquement
  • [[:space:]] Espace blanc
  • \s Tout caractère d'espacement
  • \v Espace vertical
  • \h Espace horizontal
  • x Ignorer les espaces
Fletcher Ripp
la source
5

Il me semble que l'utilisation d'un REGEX dans ce cas serait tout simplement exagéré. Pourquoi ne pas simplement strpos pour trouver le caractère espace. De plus, le caractère espace dans les expressions régulières n'a rien de spécial, vous devriez pouvoir le rechercher de la même manière que pour tout autre caractère. C'est-à-dire, à moins que vous n'ayez désactivé l'espace blanc du motif, ce qui ne serait guère nécessaire dans ce cas.

Kibbee
la source
5

En Perl, le commutateur est \s(espace blanc).

Elsporko
la source
16
Ceci est incorrect - il rassemble tous les espaces, pas seulement le caractère espace.
J. Taylor
Mais la question est balisée avec PHP, pas avec Perl.
Peter Mortensen
4

J'utilise une expression régulière pour m'assurer que je n'autorise que les lettres, les chiffres et un espace

Ensuite, c'est aussi simple que d'ajouter un espace à ce que vous avez déjà:

$newtag = preg_replace("/[^a-zA-Z0-9 ]/", "", $tag);

(note, j'ai supprimé le s|qui semblait involontaire? Certainement le sétait redondant; vous pouvez restaurer le |si vous en avez besoin)

Si vous voulez spécifiquement * un espace *, comme dans seulement un seul, vous aurez besoin d' une expression plus complexe que cela, et peut-être envisager un morceau non regex séparé de la logique.

Peter Boughton
la source
3

Vous pouvez également utiliser le \ b pour une limite de mot. Pour le nom, j'utiliserais quelque chose comme ceci:

[^\b]+\b[^\b]+(\b|$)

EDIT Modifier ceci pour être une expression régulière dans l'exemple Perl

if( $fullname =~ /([^\b]+)\b[^\b]+([^\b]+)(\b|$)/ ) {
 $first_name = $1;
 $last_name = $2;
}

MODIFIER ENCORE En fonction de ce que vous voulez:

$new_tag = preg_replace("/[\s\t]/","",$tag);
Suroot
la source
1

J'essaie [[: space:]] dans un cas où il semble que les blogueurs dans WordPress utilisent des caractères d'espace non standard. Il semble que cela fonctionnera.

Jeremy Schultz
la source
1

Utilisez-le comme ceci pour permettre un espace unique.

$newtag = preg_replace("/[^a-zA-Z0-9\s]/", "", $tag)
Ajay Singh
la source