Question

Hé, j'ai une question assez basique sur les expressions régulières. Je veux simplement renvoyer le texte à l'intérieur (et y compris) des balises body, et je sais que ce qui suit n'est pas correct, car il correspond également à tous les caractères précédant la balise d'ouverture. Je me demandais comment tu allais les sauter?

x = re.match('(.*<body).*?(</body>)', fileString)

Merci!

Était-ce utile?

La solution

Voici un exemple de code qui utilise regex pour rechercher tout le texte entre les balises <body>...</body>. Bien que cela présente certaines fonctionnalités du module re de python, notez que le module Beautiful Soup est très facile à utiliser et constitue un meilleur outil à utiliser si vous envisagez d’analyser HTML ou XML. (Voir ci-dessous un exemple d'analyse à l'aide de BeautifulSoup.)

#!/usr/bin/env python
import re

# Here we have a string with a multiline <body>...</body>
fileString='''baz<body>foo
baby foo
baby foo
baby foo
</body><body>bar</body>'''

# re.DOTALL tells re that '.' should match any character, including newlines.
x = re.search('(<body>.*?</body>)', fileString, re.DOTALL)
for match in x.groups():
    print(match)
# <body>foo
# baby foo
# baby foo
# baby foo
# </body>

Si vous souhaitez collecter tous les matches, vous pouvez utiliser re.findall:

print(re.findall('(<body>.*?</body>)', fileString, re.DOTALL))
# ['<body>foo\nbaby foo\nbaby foo\nbaby foo\n</body>', '<body>bar</body>']

et si vous envisagez d'utiliser ce modèle plus d'une fois, vous pouvez le pré-compiler:

pat=re.compile('(<body>.*?</body>)', re.DOTALL)
print(pat.findall(fileString))
# ['<body>foo\nbaby foo\nbaby foo\nbaby foo\n</body>', '<body>bar</body>']

Et voici comment vous pouvez le faire avec BeautifulSoup:

#!/usr/bin/env python
from BeautifulSoup import BeautifulSoup

fileString='''baz<body>foo
baby foo
baby foo
baby foo
</body><body>bar</body>'''
soup = BeautifulSoup(fileString)
print(soup.body)
# <body>foo
# baby foo
# baby foo
# baby foo
# </body>

print(soup.findAll('body'))
# [<body>foo
# baby foo
# baby foo
# baby foo
# </body>, <body>bar</body>]

Autres conseils

Je ne connais pas Python, mais voici un exemple rapide rassemblé à l'aide de Beautiful Soup , que je vois souvent recommandé pour l'analyse HTML en Python.

import BeautifulSoup

soup = BeautifulSoup(fileString)

bodyTag = soup.html.body.string

Cela traitera (en théorie) de toutes les complexités du HTML, ce qui est très difficile avec des réponses basées sur des regex pures, car ce n'est pas pour cela que regex a été conçu.

Vous ne pouvez pas analyser HTML avec regex. HTML n'est pas un langage courant. Utilisez plutôt un analyseur HTML tel que lxml.

 x = re.match('.*(<body>.*?</body>)', fileString)

Envisagez minidom pour l'analyse HTML.

x = re.search('(<body>.*</body>)', fileString)
x.group(1)

Moins de frappe que le résultat de la correspondance

Votre chaîne fileString contient-elle plusieurs lignes ? Dans ce cas, vous devrez peut-être le spécifier ou ignorer les lignes explicitement:

x = re.match(r"(?:.|\n)*(<body>(?:.|\n)*</body>)", fileString)

ou plus simplement avec le module re:

x = re.match(r".*(<body>.*</body>)", fileString, re.DOTALL)

x.groups()[0] doit contenir votre chaîne si x n'est pas None.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top