Précédent   Forum des professionnels en informatique > PHP > Langage > Regex
Regex Forum d'entraide sur les expressions rationnelles PHP. Avant de poster -> FAQ regex, Cours de regex et Sources de regex
Partagez cette discussion sur d'autres réseaux sociaux : Viadeo Twitter Google Facebook Digg Delicious MySpace Yahoo
Réponse Proposer ce sujet en actualité
 
Outils de la discussion
Publicité
'
Vieux 16/10/2007, 08h16   #1
Invité régulier
 
Inscription : octobre 2007
Messages : 8
Détails du profil
Informations forums :
Inscription : octobre 2007
Messages : 8
Points : 5
Points : 5
Par défaut Remplacement conditionnel via une regexp

Bonjour à tous,

Je cherche à traiter un fichier structuré ainsi :

Citation:
A blabfdsdflabla... cvsfsgtgtfgf fdsfdsfd € 452 gdsfgf € 123
_ blafdsfsdfblabla... cvsfsgttgfgf fdsfdsfd gdsfgf £ 123
B blablasfsffsdfbla... cvsfgtrgtrhfgf $ 45 fdgtgdsfd $ 335 gdsfgf $ 123
_ blabfsdffsdsfsfdlabla... cvsfsfhfgf rererzerzerzdsfdsfd € 44 gdsfgf € 123
_ blabfsdffsdsfsfdlabla... cvsfsfhfgf rererzerzerzdsfdsfd € 44 gdsfgf € 123
A blablabfsfsdla... cvsfsfgtrsdhfgf $ 654 fdsfdsfd gdsfgf $ 123
_ blablabfdsfsdla... cfdsdgvsfsfhfgf € 100 fdsfdsfd gdsfgf € 123
A blablafsdfsbla... cvsffdgdfggsfhfgf £ 44 fdsfdgfdgdffsfssfsf fsdfd gdsfgf £ 123
Toutes les lignes commencent soit par une lettre, soit par un _
Dans le cas où les lignes ne commencent pas par _, je veux coloriser tous les prix qui se trouvent sur la ligne. Les prix sont systématiquement précédés de $ £ ou € suivi et précédé d'un blanc
Pour les lignes qui commencent par un _, je ne veux rien faire du tout car ces items sont épuisés


J'ai écrit ceci en php :


Code :
1
2
3
4
5
6
7
8
9
function maj_prix($capture)
{
if ($capture[1] != "_") $maj = "<span class='prix'>".$capture[4]."</span>";
else $maj = $capture[4];
$txt = $capture[1].$capture[2].$capture[3].$maj;
return $txt;
}
 
$texte = preg_replace_callback('#^(.)(.*?)( [$€£] )([0-9,]+)#m', "maj_prix", $texte);
Cela ne fonctionne pas trop mal, cela ne touche pas aux lignes avec des _.
Le seul problème c'est que cela ne transforme que le premier prix de la ligne dans le cas où je mets le non-gourmant (.*?)



Citation:
A blabfdsdflabla... cvsfsgtgtfgf fdsfdsfd € <span class='prix'>452</span> gdsfgf € 123
_ blafdsfsdfblabla... cvsfsgttgfgf fdsfdsfd gdsfgf £ 123
B blablasfsffsdfbla... cvsfgtrgtrhfgf $ <span class='prix'>45</span> fdgtgdsfd $ 335 gdsfgf $ 123
_ blabfsdffsdsfsfdlabla... cvsfsfhfgf rererzerzerzdsfdsfd € 44 gdsfgf € 123
_ blabfsdffsdsfsfdlabla... cvsfsfhfgf rererzerzerzdsfdsfd € 44 gdsfgf € 123
A blablabfsfsdla... cvsfsfgtrsdhfgf $ <span class='prix'>654</span> fdsfdsfd gdsfgf $ 123
_ blablabfdsfsdla... cfdsdgvsfsfhfgf € 100 fdsfdsfd gdsfgf € 123
A blablafsdfsbla... cvsffdgdfggsfhfgf £ <span class='prix'>44</span> fdsfdgfdgdffsfssfsf fsdfd gdsfgf £ 123

Et en remplaçant le non-gourmand (.*?) par un gourmand (.+), cela ne remplace que la dernière occurence, donc ce n'est pas suffisant non plus :

Citation:
A blabfdsdflabla... cvsfsgtgtfgf fdsfdsfd € 452 gdsfgf € <span class='prix'>123</span>
_ blafdsfsdfblabla... cvsfsgttgfgf fdsfdsfd gdsfgf £ 123
B blablasfsffsdfbla... cvsfgtrgtrhfgf $ 45 fdgtgdsfd $ 335 gdsfgf $ <span class='prix'>123</span>
_ blabfsdffsdsfsfdlabla... cvsfsfhfgf rererzerzerzdsfdsfd € 44 gdsfgf € 123
_ blabfsdffsdsfsfdlabla... cvsfsfhfgf rererzerzerzdsfdsfd € 44 gdsfgf € 123
A blablabfsfsdla... cvsfsfgtrsdhfgf $ 654 fdsfdsfd gdsfgf $ <span class='prix'>123</span>
_ blablabfdsfsdla... cfdsdgvsfsfhfgf € 100 fdsfdsfd gdsfgf € 123
A blablafsdfsbla... cvsffdgdfggsfhfgf £ 44 fdsfdgfdgdffsfssfsf fsdfd gdsfgf £ <span class='prix'>123</span>
Je dois passer à côté de quelque chose mais je ne parviens pas à colorer tous les prix de mes lignes (ne commençant pas par _) mais uniquement soit le premier, soit le dernier.

Pouvez-vous m'aider à colorer tous mes prix des lignes ne commençant pas par _ si possible sans faire de boucle ?

Merci d'avance.
Tibalpa est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 16/10/2007, 17h33   #2
Nouveau Membre du Club
 
Inscription : janvier 2005
Messages : 27
Détails du profil
Informations personnelles :
Âge : 30
Localisation : France, Paris (Île de France)

Informations forums :
Inscription : janvier 2005
Messages : 27
Points : 31
Points : 31
Lu,

déjà tu peux simplifier ton expression :

Code :
1
2
3
4
5
6
7
8
9
10
11
<?php
function maj_prix($capture)
{
 
$maj = "<span class='prix'>".$capture[4]."</span>";
$txt = $capture[1].$capture[2].$capture[3].$maj;
return $txt;
}
 
$texte = preg_replace_callback('#^([^_]{1})(.+?)( [$€£] )([0-9,]+)#m', "maj_prix", $texte);
?>
Ensuite Si tu Testes le premier caractère de la chaine alors tout logiquement, ta règle au premier prix et n'iras pas voir ailleurs. Du coup, une fonction avec encore un masque va pouvoir le faire

En gros si ligne ne commence pas par _ , je change :

Code :
1
2
3
4
5
6
7
8
9
function maj_prix($capture) {
 
	$Masque = '`([€£$\s]{1,2})([0-9,]+)`iS';
	$texte  = preg_replace($Masque, "$1" . ' <span class="prix">'. "$2" .'</span>', $capture[2]);
 
	return $capture[1] . $texte;
	}
 
$texte = preg_replace_callback('#^([^_]{1})(.+?)$#m', "maj_prix", $texte);
Bon courage ^^
zebden est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 16/10/2007, 22h07   #3
Invité régulier
 
Inscription : octobre 2007
Messages : 8
Détails du profil
Informations forums :
Inscription : octobre 2007
Messages : 8
Points : 5
Points : 5
Un très, très grand merci, cela fonctionne impeccable.


Le seul petit bémol c'est que cela va générer autant d'appels à preg_replace qu'il y a de lignes de concernées, donc si mon fichier fait 1000 lignes, environ 750 preg_replace (car il y a une moyenne de 25% de désactivés dans le fichier)

En fait je voulais éviter les boucles et je cherchais la regexp qui pourrait tout résoudre en une seule passe.
Mais après de multiples tentatives... à moins que quelqu'un ne trouve une formule magique... je crois que je vais effectivement me rabattre sur votre solution qui a le mérite de fonctionner.


En tout cas un grand merci.
Tibalpa est déconnecté   Envoyer un message privé Réponse avec citation 00
Réponse Proposer ce sujet en actualité Cette discussion est résolue.
Outils de la discussion



Fuseau horaire GMT +2. Il est actuellement 22h34.


 
 
 
 
Partenaires

Hébergement Web