Discussion:
[HS] Expression reguliere.
(trop ancien pour répondre)
WebShaker
2010-02-14 20:50:46 UTC
Permalink
Salut.

bon je pense pas que ma question soit en phase avec le PHP mais comme je
ne sais pas ou la poser...

J'essaye de parser un fichier qui contient

CREATE OBJECT my_object
POS 10,20
HERITAGE parent
NO CACHE;


j'ai donc crée une expression réguliere qui est la suivante
"/CREATE OBJECT\s+(\S*)\s+(.*)(HERITAGE\s+(\d+))?(.*);/Uis";

mais cela ne marche pas.
je précise que je ne connais pas l'ordre des option de l'objet.
j'aurai tres bien pu avoir a parser

CREATE OBJECT my_object
HERITAGE parent
POS 10,20
NO CACHE;

En gros je ne sais pas ou se trouve HERITAGE dans le texte.

Quelqu'un peut il m'aider.
ou faut-il que je fasse deux expression régulière:
l'une pour trouver
POS 10,20
HERITAGE parent
NO CACHE

et la seconde pour trouver la dedans
HERITAGE parent

Merci.
Etienne
Olivier Miakinen
2010-02-14 22:40:51 UTC
Permalink
Bonjour,
Post by WebShaker
bon je pense pas que ma question soit en phase avec le PHP mais comme je
ne sais pas ou la poser...
Le groupe approprié est fr.comp.lang.regexp. J'y fais suivre le discussion.
Post by WebShaker
J'essaye de parser un fichier qui contient
CREATE OBJECT my_object
POS 10,20
HERITAGE parent
NO CACHE;
Ok, mais tu manques un peu de précision. Qu'est-ce qui est fixe là
dedans et qu'est-ce qui est variable ? Par exemple, est-ce que la
chaîne « parent » est composée de ces six lettres exclusivement, ou bien
est-ce que n'importe quelle autre chaîne conviendrait ? Je vais supposer
que ça peut être n'importe quelle chaîne ne comportant aucun caractère
blanc. Par ailleurs, te suffit-il de vérifier que tu trouves bien une
séquence ressemblant à ça, ou bien veux-tu en outre *extraire* une ou
plusieurs sous-chaînes ?
Post by WebShaker
j'ai donc crée une expression réguliere qui est la suivante
"/CREATE OBJECT\s+(\S*)\s+(.*)(HERITAGE\s+(\d+))?(.*);/Uis";
Ok pour le flag /s qui te permet de prendre en compte les sauts de ligne
avec le métacaractère '.'. Ok aussi pour le flag /U qui assure la non
gourmandise par défaut. Quant au flag /i, si tu écris CREATE, OBJECT et
HERITAGE toujours en majuscules, il n'est pas indispensable (mais il ne
gêne pas non plus, surtout si tu ne contrôles pas toujours la casse des
mots-clés).

En revanche, à moins que ce que tu as désigné par « parent » soit en
fait un nombre entier (« HERITAGE 307 » par exemple), cette partie de
l'expression rationnelle ne sera jamais prise en compte (mais peu
importe puisque tu l'as mise optionnelle du fait du '?').
Post by WebShaker
mais cela ne marche pas.
Il faudrait savoir ce que tu attends exactement comme résultat. Avec
l'exemple que tu as donné, ça devrait marcher, avec comme résultat de
capture pour les 5 paires de parenthèses :

$1 = "my_object"
$2 = "POS 10,20
HERITAGE parent
NO CACHE"
$3 = ""
$4 = ""
$5 = ""

Note que si tu ne cherches pas à capturer quoi que ce soit tu peux
économiser quelques parenthèses pour le même résultat :
"/CREATE OBJECT\s+\S*\s+.*(HERITAGE\s+\d+)?.*;/Uis"
Post by WebShaker
je précise que je ne connais pas l'ordre des option de l'objet.
j'aurai tres bien pu avoir a parser
CREATE OBJECT my_object
HERITAGE parent
POS 10,20
NO CACHE;
En gros je ne sais pas ou se trouve HERITAGE dans le texte.
Mais il faut absolument qu'il se trouve quelque part, alors qu'on se
fout des autres ? Et c'est la valeur suivant HERITAGE que tu veux
capturer ? Si oui, et en supposant que tu veux au moins vérifier qu'il
n'y a rien d'autre que des POS, des HERITAGE et des NO CACHE, voici
comment je procèderais.


Voyons d'abord chaque ligne individuellement.

"CREATE OBJECT my_object"
-> /CREATE\s+OBJECT\s+\S+/

"HERITAGE parent" (avec capture de parent)
-> /HERITAGE\s+(\S+)/

"POS 10,20"
-> /POS\s+\d+,\d+/ (rajouter au besoin des \s* autour de la virgule)

"NO CACHE"
-> /NO\s+CACHE/


Si seul le CREATE OBJECT et le HERITAGE t'intéressent et qu'il peut y
avoir n'importe quoi d'autre avant et après, autant ne pas s'embêter
avec les POS et NO CACHE. On peut même remplacer les '.' dans la regexp
par des [^;], ce qui permet de se passer à la fois des flags U et s.

/CREATE\s+OBJECT\s+\S+[^;]*\s+HERITAGE\s+(\S+)[^;]*;/i


Maintenant, si tu veux en outre vérifier la syntaxe des POS et des NO
CACHE mais pas leur position, tu peux essayer :

/CREATE\s+OBJECT\s+\S+(?:\s+(?:POS\s+\d+,\d+|NO\sCACHE))*\s+HERITAGE\s+(\S+)(?:\s+(?:POS\s+\d+,\d+|NO\sCACHE))*;/i


Cordialement,
--
Olivier Miakinen
Continuer la lecture sur narkive:
Loading...