2011-12-28 6 views
5

Sto cercando di analizzare il codice html indicato sotto utilizzando lxml.html e utilizzando CSSSelector anziché XPath.Python: selettore CSS da utilizzare all'interno di lxml.cssselect

link = doc.cssselect('html body div.results dl dt a) 

il codice di cui sopra mi sta dando content-1 e content-2 come uscita ma il mio output desiderato è link 1 link 2. Così ho sostituito il mio codice con

link = doc.cssselect('html body div.results dl dt a[href]') 

ma sto ancora ottenendo lo stesso risultato. Quindi la mia domanda è qual è il corretto selettore CSS per ottenere l'attributo href.

   <div class = "results"> 
        <div> some tags here </div> 
         <dl> 
           <dt title = "My Title 1" style = "background: transparent url('/img/accept.png') no-repeat right center"> 
           <a href = "/link 1"> content-1</a> 
           </dt> 
         </dl> 

         <dl> 
          <dt title = "My Title 2" style = "background: transparent url('/img/accept.png') no-repeat right center"> 
          <a href = "/link 2">content-2</a> 
          </dt> 
        </dl> 
      </div> 

risposta

6

Io credo non è possibile ottenere il valore di attributo tramite selettori CSS. Si dovrebbe ottenere gli elementi ...

>>> elements = doc.cssselect('div.results dl dt a') 

... e quindi ottenere gli attributi da loro:

>>> for element in elements: 
...  print element.get('href') 
... 
/link 1 
/link 2 

Naturalmente, list comprehension sono i tuoi amici:

>>> [element.get('href') for element in elements] 
['/link 1', '/link 2'] 

Dal non è possibile aggiornare le proprietà degli attributi nei CSS, credo che non abbia senso ottenerli attraverso i selettori CSS. Puoi "menzionare" gli attributi nei selettori CSS da recuperare solo per abbinare i loro elementi. Tuttavia, è solo cogitazione e potrei sbagliarmi; se io sono, per favore qualcuno mi corregga :) Bene, @ Tim Diggs conferma la mia ipotesi di sotto :)

EDIT: Ora è possibile farlo usando pseudo-selettori per esempio:

doc.cssselect('div.results dl dt a::attr('href')') 

Ciò restituirà la attributo href di ciascun link.

+0

Ho appena capito da solo.Comunque grazie per la risposta – RanRag

+0

@brandizzi, hai ragione - puoi selezionare solo elementi in css, non attributi - le parentesi servono per filtrare quali elementi selezionare (ma non è una cattiva idea selezionare solo i tag senza attributi href (che è ciò che fa [href]) –

+0

@RanRag, dovresti spuntare la risposta di brandizzi come corretta anche se alla fine non ne avevi bisogno. –

3

È necessario ottenere l'attributo sul risultato di cssselect (che restituisce sempre l'elemento, non un attributo):

primo luogo, io non sono sicuro di doc.cssselect (ma forse questo è il vostro propria funzione ?)

lxml.cssselect viene normalmente usato:

from lxml.cssselect import CSSSelector 
sel = CSSSelector('html body div.results dl dt a[href]') 

allora, supponendo che hai già un documento

links = [] 
for a_href in sel(doc): 
    links.append(a_href.get('href')) 

o il più succinto:

links = [a_href.get('href') for a_href in doc.cssselect('html body div.results dl dt a[href]')] 
+1

fondamentalmente doc equivale a 'doc = lxml.html.fromstring (content)' dove il contenuto è i miei dati html dalle funzioni 'urllib e read' – RanRag

2

Ho usato con successo

#element-id ::attr(value) 

Per ottenere l'attributo "valore" per gli elementi HTML.

0

lxml cssselector funziona con la selezione degli attributi. Sotto il codice è possibile selezionare l'attributo src dall'elemento di script HTML.

select = cssselect.CSSSelector("script[src]") 
    links = [ el.get('src') for el in select(dochtml) ] 
    links=iter(links) 
    for n, l in enumerate(links): 
     print n, l