Expression régulière

Expression régulière - Python - Programmation

Marsh Posté le 03-05-2005 à 16:14:27    

Bonjour,
 
J'ai un petit script en python avec un vilain if :  

Code :
  1. if filename.find('.php') != -1 or filename.find('.html') != -1 or filename.find('.htm') != -1 or filename.find('.tpl') != -1 or filename.find('.css') != -1:


 
Je suis sur qu'il y a moyen de gérer ça autrement avec une expression régulière mais je n'y connais pas grand chose dans ce domaine (en regexp et en python c'est mon premier script)
 
Si une bonne ame pouvait me montrer le bon chemin  
 
Merci

Reply

Marsh Posté le 03-05-2005 à 16:14:27   

Reply

Marsh Posté le 03-05-2005 à 16:27:41    

Faut que tu te plonges dans le module python re.
Sinon moins laid :

Code :
  1. if filename[-4:] == '.php': etc...


 
@++


---------------
Du taf dans le Logiciel Libre : https://www.linuxjobs.fr
Reply

Marsh Posté le 03-05-2005 à 16:31:26    

très juste je me suis plongé dans le module re. Mais je suis une vraie bille en regexp :(

Reply

Marsh Posté le 03-05-2005 à 16:46:16    

r"(\.html|\.css|\.htm|\.php|\.tpl)$"


 
Suffit de faire un search dessus [:spamafote]
 
Tu devrais installer Kodos, et lire Dive Into Python (il me semble qu'il y a un chapitre sur les REs)


Message édité par masklinn le 03-05-2005 à 16:47:19

---------------
Stick a parrot in a Call of Duty lobby, and you're gonna get a racist parrot. — Cody
Reply

Marsh Posté le 03-05-2005 à 16:47:47    

Merci beaucoup
 
Je viens d'installer Kodos et je vais passer ma soirée sur les regexp, c'est vraiment une lacune chez moi
 


Message édité par Monsieur Seb le 03-05-2005 à 16:48:09
Reply

Marsh Posté le 03-05-2005 à 18:43:22    

une autre solution :

Code :
  1. ext=["php", "html", "css", "htm", "tpl" ]
  2. filename = "test.html"
  3. if filename.split("." )[-1] in ext:
  4.     print "ok"
  5.    
  6. ok


 
le_GLu


---------------
Python facile : http://pythonfacile.free.fr/ Les ressources (liens) en français sur Python.
Reply

Marsh Posté le 03-05-2005 à 19:35:49    

tu peux utiliser .endswith aussi :o

Reply

Marsh Posté le 03-05-2005 à 19:46:05    

j'aime beaucoup ta méthode le_GLu !
 
endswith à l'air pas mal aussi
 
merci à tous

Reply

Marsh Posté le 03-05-2005 à 20:04:31    

sauf que la méthode de glu le_GLu, elle va te péter à la gueule si y a pas de . dans le nom du fichier

Reply

Marsh Posté le 03-05-2005 à 22:47:20    

Bien après un peu d'apprentissage j'ai décidé d'utiliser les regexp, beaucoup plus simple et élégant au final.
 
Le script (mon premier en python) compte juste le nombre de ligne dans un projet web en php.
Je le colle ici pour info :  
 

Code :
  1. import os.path
  2. import string
  3. import re
  4. def listRep(args, dirname, filenames):
  5.     global nbLine
  6.     rawstr = r"""(\.html|\.css|\.htm|\.php|\.tpl|\.txt)$""" 
  7.     for filename in filenames:
  8.             if re.search(rawstr, filename) != None:
  9.                 filePath = dirname + '/' + filename
  10.                 hFile = open(filePath, 'r' )
  11.                 lenFile = len(hFile.readlines())
  12.                 hFile.close()
  13.                 nbLine += lenFile
  14. nbLine = 0               
  15. os.path.walk('/home/seb/projets/seblog', listRep, None)
  16. print nbLine;


 
Bon ... il y a des choses en dur (le path de racine et le séparateur) mais bon c'est juste pour faire joujou pour l'instant. Je suis toutefois preneur d'observation constructive !
 
Merci de votre aide  :jap:

Reply

Marsh Posté le 03-05-2005 à 22:47:20   

Reply

Marsh Posté le 04-05-2005 à 00:46:06    

  • Pq des triples guillements autour de ta regexp ?
  • Utilise os.path.join(dirname, filename) au lieu de dirname + '/' + filename
  • 'r' est le mode d'ouverture par défaut, pas besoin de le préciser
  • readlines() charge tout ton fichier en mémoire. J'aurais plutôt fait: for line in file: nbLine += 1
  • il n'est pas nécessaire de fermer le fichier explicitement, c'est fait automatiquement lorsque le compteur de référence tombe à 0 (du moins en CPython).
  • les variables globales c'est moche (pour un script aussi court c'est pas vraiment un problème mais bon...). On peut profiter de l'argument supplémentaire de os.path.walk pour passer une référence à un object, qui sera donc modifiable. Le plus simple, c'est une liste avec un seul élément.


Tout ça ensemble, ça donne:

Code :
  1. def listRep(nbLines, dirname, filenames):
  2.     rawstr = r"(\.html|\.css|\.htm|\.php|\.tpl|\.txt)$"
  3.     for filename in filenames:
  4.             if re.search(rawstr, filename):
  5.                 filePath = os.path.join(dirname, filename)
  6.                 for line in file(filePath):
  7.                     nbLines[0] += 1
  8. nbLine = [0]
  9. os.path.walk('/home/seb/projets/seblog', listRep, nbLine)
  10. print nbLine[0]


Maintenant, le coup de la liste, je trouve ça un peu moche quand-même, mais je vois pas trop comment faire autrement sans passer par une globale. J'aurais sans doute utilisé os.walk au lieu de os.path.walk:

Code :
  1. nbLine = 0
  2. for dirname, dirnames, filenames in os.walk('/home/seb/projets/seblog'):
  3.     rawstr = r"(\.html|\.css|\.htm|\.php|\.tpl|\.txt)$"
  4.     for filename in filenames:
  5.             if re.search(rawstr, filename):
  6.                 filePath = os.path.join(dirname, filename)
  7.                 for line in file(filePath):
  8.                     nbLine += 1
  9. print nbLine


edit: j'ai oublié les import, rien de grave


Message édité par dividee le 04-05-2005 à 00:47:34
Reply

Marsh Posté le 04-05-2005 à 08:05:31    

c'est quoi l'intérêt d'utiliser une regex de la mort qui tue (d'ailleurs, pas optimisée) si on la compile pas :o

Reply

Marsh Posté le 04-05-2005 à 09:20:50    

dividee> merci pour tes remarques  :jap: ! python à l'aire plus simple syntaxiquement que d'autre langage, mais j'ai des réflexes de dev en syntaxe c/c++/java. Pour le coup des triples guillement, c'est Kodos qui me sort ça dans ses examples  
 
Taz> tu pourrais juste donner un petit mot sur la compilation des regexp et de l'impacte sur les performances  :whistle:

Reply

Marsh Posté le 04-05-2005 à 09:34:20    

RTFM
re.compile

Reply

Marsh Posté le 04-05-2005 à 11:41:50    

Taz a raison, la regexp est utilisée très souvent, alors tu y gagneras bcp à la compiler. En fait, je pense que la version plus "naïve" avec le .endswith serait encore plus rapide, même si c'est moins beau...

Reply

Marsh Posté le 04-05-2005 à 12:25:08    

je suis d'accord, sauf que je trouve la version endswith pas si moche que ça.

Reply

Sujets relatifs:

Leave a Replay

Make sure you enter the(*)required information where indicate.HTML code is not allowed