2009-05-11 22 views
6

considerar lo siguiente:Python - Regex - ¿Cómo encontrar una cadena entre dos juegos de cuerdas

<div id=hotlinklist> 
    <a href="foo1.com">Foo1</a> 
    <div id=hotlink> 
    <a href="/">Home</a> 
    </div> 
    <div id=hotlink> 
    <a href="/extract">Extract</a> 
    </div> 
    <div id=hotlink> 
    <a href="/sitemap">Sitemap</a> 
    </div> 
</div> 

Cómo haría usted para sacar la línea de mapa del sitio con expresiones regulares en Python ?

<a href="/sitemap">Sitemap</a> 

Lo siguiente se puede utilizar para extraer las etiquetas de anclaje.

'/<a(.*?)a>/i' 

Sin embargo, hay varias etiquetas de delimitación. También hay múltiples enlaces de acceso rápido, así que tampoco podemos usarlos realmente?

+0

Es probable que escuche que las expresiones regulares no son adecuados para analizar un libre de contexto lenguaje como HTML. – Gumbo

+2

Si es usted el que genera ese código HTML, vale la pena señalar que múltiples atributos idénticos 'id =' como ese no son válidos. Una 'clase =' es más apropiada. –

Respuesta

13

No utilice un regex. Use BeautfulSoup, un analizador de HTML.

from BeautifulSoup import BeautifulSoup 

html = \ 
""" 
<div id=hotlinklist> 
    <a href="foo1.com">Foo1</a> 
    <div id=hotlink> 
    <a href="/">Home</a> 
    </div> 
    <div id=hotlink> 
    <a href="/extract">Extract</a> 
    </div> 
    <div id=hotlink> 
    <a href="/sitemap">Sitemap</a> 
    </div> 
</div>""" 

soup = BeautifulSoup(html) 
soup.findAll("div",id="hotlink")[2].a 

# <a href="/sitemap">Sitemap</a> 
6

¡Analizar HTML con expresiones regulares es una mala idea!

pensar en el siguiente fragmento de HTML

Hay muchos más ejemplos de este tipo. Las expresiones regulares son buenas para muchas cosas, pero no para analizar HTML.

Debería considerar usar Beautiful Soup analizador de HTML python.

De todos modos, una solución ad-hoc utilizando expresiones regulares es

import re 

data = """ 
<div id=hotlinklist> 
    <a href="foo1.com">Foo1</a> 
    <div id=hotlink> 
    <a href="/">Home</a> 
    </div> 
    <div id=hotlink> 
    <a href="/extract">Extract</a> 
    </div> 
    <div id=hotlink> 
    <a href="/sitemap">Sitemap</a> 
    </div> 
</div> 
""" 

e = re.compile('<a *[^>]*>.*</a *>') 

print e.findall(data) 

Salida:

>>> e.findall(data) 
['<a href="foo1.com">Foo1</a>', '<a href="/">Home</a>', '<a href="/extract">Extract</a>', '<a href="/sitemap">Sitemap</a>'] 
+0

Si reemplaza '. *' Con '(?: [^ <] + | <(!/A \ b)) *', obtendrá menos falsos positivos, sin explotar el motor de expresiones regulares con retroceso. –

1

Uso BeautifulSoup o lxml si necesita analizar HTML.

Además, ¿qué es lo que realmente necesita hacer? Encuentra el último enlace? Encuentra el tercer enlace? Encuentra el enlace que apunta a/sitemap? No está claro por tu pregunta. ¿Qué necesita para do con los datos?

Si realmente tiene que usar expresiones regulares, eche un vistazo a findall.

5

Con el fin de extraer el contenido de la coletilla:

<a href="/sitemap">Sitemap</a> 

... yo usaría:

>>> import re 
    >>> s = ''' 
    <div id=hotlinklist> 
    <a href="foo1.com">Foo1</a> 
     <div id=hotlink> 
     <a href="/">Home</a> 
     </div> 
     <div id=hotlink> 
     <a href="/extract">Extract</a> 
     </div> 
     <div id=hotlink> 
     <a href="/sitemap">Sitemap</a> 
     </div> 
    </div>''' 
    >>> m = re.compile(r'<a href="/sitemap">(.*?)</a>').search(s) 
    >>> m.group(1) 
    'Sitemap' 
+0

En realidad, reemplace el sitemap con XYZ, ya que realmente puede ser cualquier cosa. Solo sabría que es el 3er div dentro de la div en la lista de hotlinlist. El patrón html que se utiliza puede repetirse muchas veces. Digamos que quiero sacar todos los teléfonos inteligentes que figuran en eBay. Sé que el patrón anterior se repite para cada teléfono inteligente que se encuentra, sin embargo, el XYZ puede ser un iPhone, Blackberry, Nokia o cualquier otro teléfono inteligente. No podría haber ningún artículo o 100s. Por lo tanto, estaba buscando algo que diga encontrar el patrón repetido, luego saque la línea del teléfono inteligente y tenga una lista de teléfonos inteligentes. – un33k

+0

Me gusta esto ya que responde la pregunta. También me ayudó a comprender mejor la expresión regular, créanlo o no. – Max

Cuestiones relacionadas