2014-12-01 12 views
8

Sto usando rvest per analizzare un sito web. Sto colpendo un muro con questi piccoli spazi non-breaking. Come si rimuove lo spazio bianco creato dall'elemento   in un documento html analizzato?parsing html contenente spazio non freni

library("rvest") 
library("stringr") 

minimal <- html("<!doctype html><title>blah</title> <p>&nbsp;foo") 

bodytext <- minimal %>% 
    html_node("body") %>% 
    html_text 

ora ho estratto il corpo del testo:

bodytext 
[1] " foo" 

Tuttavia, non posso rimuovere quel po 'fastidioso di spazi bianchi!

str_trim(bodytext) 

gsub(pattern = " ", "", bodytext) 

risposta

3

I &nbsp sta per "non-breaking space" che, nello spazio unicode, ha il proprio carattere distinto da uno spazio "normale" (cioè " "). Confronta

charToRaw(" foo") 
# [1] 20 66 6f 6f 
charToRaw(bodytext) 
# [1] c2 a0 66 6f 6f 

Quindi si desidera utilizzare una delle classi di caratteri speciali per lo spazio bianco. È possibile rimuovere tutti gli spazi bianchi con

gsub("\\s", "", bodytext) 

Su Windows, avevo bisogno di assicurarsi che la codifica della stringa è stata impostata correttamente

Encoding(bodytext) <- "UTF-8" 
gsub("\\s", "", bodytext) 
+0

che la funzione 'charToRaw' è meravigliosa! OK, quindi ho effettivamente provato qualcosa di simile. Come da [questa risposta] (http://stackoverflow.com/questions/4515117/php-parsing-problem-nbsp-and-%C3%82), il ' ' viene interpretato come" Â "e" ". Il problema è che mentre potrei far corrispondere la "" con una regex, non posso farlo con lo spazio. Il tuo trucco di codifica non ha aiutato. Perdonami per non aver riprodotto questo lavoro qui; Non riesco a ottenere il "Â" da replicare nel mio esempio – AndrewMacDonald

+0

Vedrai la "Â" se non hai la codifica correttamente impostata sulla variabile. Cosa ottieni se esegui 'Encoding (bodytext)'? Probabilmente si può anche tranquillamente impostarlo su "latin1" – MrFlick

+2

'Encoding (bodytext)' restituisce 'UTF-8', tuttavia ciò che appare come uno spazio vuoto non può essere confrontato con alcuna espressione che indirizzi gli spazi, né' \\ s' né ' [: space:] ' – AndrewMacDonald

7

jdharrison rispose:

gsub("\\W", "", bodytext) 

e, che funzionerà ma è possibile utilizzare:

gsub("[[:space:]]", "", bodytext) 

che rimuoverà tutto Space characters: tab, newline, vertical tab, form feed, carriage return, space and possibly other locale-dependent characters. È un'alternativa molto leggibile ad altre classi regex criptiche.

+2

Purtroppo quest'ultima soluzione, per quanto leggibile, non funziona. Il problema sembra implicare la codifica (vedi il mio commento a @MrFlick) – AndrewMacDonald

+0

Tuttavia, la tecnica '\\ W' funziona! Quindi apparentemente, qualunque sia lo spazio che è codificato come nel mio locale, NON è una parola! – AndrewMacDonald

+0

deselezionata perché mentre funziona, rimuovere i caratteri non word è troppo estremo per la mia applicazione, e voglio ancora sapere come abbinare questo spazio! – AndrewMacDonald

0

L'utilizzo di rex può semplificare questo tipo di attività. Inoltre, non sono in grado di riprodurre i problemi di codifica, quanto segue sostituisce correttamente lo spazio indipendentemente dalla codifica sulla mia macchina. (E 'la stessa soluzione [[:space:]] però, così probabilmente ha lo stesso problema per voi)

re_substitutes(bodytext, rex(spaces), "", global = TRUE) 

#> [1] "foo" 
7

ho incontrato lo stesso problema, e si sono stabiliti sulla semplice sostituzione di

gsub(intToUtf8(160),'',bodytext) 

(Modificato per correggere caso.)

2

Pubblicare questo poiché penso che sia l'approccio più robusto.

ho raschiato una pagina di Wikipedia e ottenuto questo nella mia uscita (non è sicuro se sarà copiare-incollare correttamente):

x <- " California" 

E gsub("\\s", "", x) non ha cambiato nulla, che ha sollevato la bandiera che qualcosa di sospetto sta succedendo.

a indagare, ho fatto:

dput(charToRaw(strsplit(x, "")[[1]][1])) 
# as.raw(c(0xc2, 0xa0)) 

di capire come esattamente quel personaggio viene memorizzato/riconosciuto in memoria.

Con questo in mano, possiamo usare gsub un po 'più robusto rispetto alle altre soluzioni:

gsub(rawToChar(as.raw(c(0xc2, 0xa0))), "", x) 
# [1] "California" 

(@ suggerimento di MrFlick per impostare la codifica non ha funzionato per me, e non è chiaro dove @shabbychef ha ottenuto l'ingresso 160 per intToUtf8; questo approccio può essere generalizzato ad altre situazioni analoghe)

0

sono stato in grado di rimuovere &nbsp; spazi all'inizio e alla fine di stringhe con mystring %>% stringr::str_trim().