2010-10-20 5 views
2

J'essaye d'analyser une liste de données d'un fichier en utilisant python - mais je ne veux pas extraire les données qui sont mises en commentaire. Un exemple de la façon dont les données sont structurées est:Lookbehind négatif dans les expressions régulières Python

#commented out block 
uncommented block 
# commented block 

Je suis en train de récupérer uniquement l'élément intermédiaire, donc essaie d'exclure les éléments avec hash au début. Le problème est que certains hash sont juste à côté des articles commentés, et certains ne coûtent pas, et l'expression que j'ai actuellement ne fonctionne que si les articles ont été commentés dans le premier exemple ci-dessus -

(?<!#)(commented) 

J'ai essayé d'ajouter \ s + à le lookahead négatif mais ensuite je reçois une plainte que l'expression n'a pas une longueur maximale évidente. Y a-t-il un moyen de faire ce que je tente de faire?

Merci à l'avance,

Dan

+0

Peut-être que vous avez besoin juste quelque chose comme '^ ([^ #]. *)' – Andrew

Répondre

6

Pourquoi utiliser regex? Méthodes de chaîne feraient très bien:

>>> s = """#commented out block 
uncommented block 
# commented block 
""".splitlines() 
>>> for line in s: 
    not line.lstrip().startswith('#') 


False 
True 
False 
+1

+1 Regexes sont grands ... pour certains problèmes. Pour d'autres, il existe de bien meilleures solutions (et moins cryptiques);) – delnan

+1

+1: utilisez le bon outil pour le travail. Il n'est pas toujours nécessaire de faire ressortir le marteau. – JoshD

+0

J'ai fini par faire une combinaison de recherche d'expression régulière et ensuite vérifier les résultats pour #s au début. Je voulais seulement extraire certaines sections d'un fichier, qui contenait certains bits, d'où la raison pour laquelle j'ai utilisé regex pour rechercher ces pièces. – Dan

4

Comme indiqué SilentGhost, une expression régulière est pas la meilleure solution à ce problème, mais je pensais que j'adresse le regard négatif derrière.

Vous avez pensé à faire:

(?<!#\s+)(commented) 

Cela ne fonctionne pas, parce que le regard a besoin derrière une longueur finie. Vous pouvez faire quelque chose comme ceci:

(?<!#)(\s+commented) 

Cela correspond aux lignes que vous voulez, mais bien sûr, vous auriez à dépouiller les espaces blancs au large du groupe de commentaires. Encore une fois, la manipulation des cordes est meilleure pour ce que vous faites, mais je voulais montrer à quel point le regard négatif pouvait marcher puisque vous demandiez.

0
>>> s = """#commented out block 
... uncommented block 
... # commented block 
... """ 
>>> for i in s.splitlines(): 
... if not i.lstrip().startswith("#"): 
...  print i 
... 
uncommented block 
Questions connexes