Domanda

Ho un (piuttosto complesso) web scraping sfida che voglio realizzare e piacerebbe per qualche direzione (a qualsiasi livello avete voglia di condividere) ecco qui:

Vorrei passare attraverso tutte le "specie" pagine presenti in questo link:

http://gtrnadb.ucsc.edu/

Quindi, per ciascuno di essi andrò a:

  1. Il link alla pagina di specie (ad esempio: http://gtrnadb.ucsc.edu/Aero_pern/)
  2. E poi alla "strutture secondarie" pagina link (ad esempio: http: / /gtrnadb.ucsc.edu/Aero_pern/Aero_pern-structs.html )

All'interno che puntano desidero scartare i dati nella pagina in modo che avrò una lunga lista contenente questi dati (per esempio):

chr.trna3 (1-77)    Length: 77 bp
Type: Ala   Anticodon: CGC at 35-37 (35-37) Score: 93.45
Seq: GGGCCGGTAGCTCAGCCtGGAAGAGCGCCGCCCTCGCACGGCGGAGGcCCCGGGTTCAAATCCCGGCCGGTCCACCA
Str: >>>>>>>..>>>>.........<<<<.>>>>>.......<<<<<.....>>>>>.......<<<<<<<<<<<<....

Dove ogni riga avrà un proprio elenco (all'interno della lista per ogni "tRNA" all'interno della lista per ogni animale)

Mi ricordo imbattersi i pacchetti Rcurl e XML (in R) che possono consentire per un tale compito. Ma io non so come usarli. Allora, cosa mi piacerebbe avere è: 1. Alcuni suggerimenti su come costruire un tale codice. 2. E raccomandazione per come imparare le conoscenze necessarie per l'esecuzione di un tale compito.

Grazie per qualsiasi aiuto,

Tal

È stato utile?

Soluzione

Tal,

Si potrebbe usare R e il pacchetto XML per fare questo, ma (maledetto), che è un po 'di HTML mal formato si sta cercando di analizzare. In realtà, nella maggior parte dei casi il vostro vorrebbe essere utilizzando la funzione readHTMLTable(), che è coperto in questa discussione precedente .

Dato questo brutto HTML, tuttavia, dovremo usare il pacchetto RCurl per tirare il codice HTML grezzo e creare alcune funzioni personalizzate di analizzarlo. Questo problema ha due componenti:

  1. Ottieni tutti gli URL genoma dalla pagina web di base ( http://gtrnadb.ucsc.edu/) utilizzando la funzione getURLContent() nel RCurlpackage e qualche magia regex: -)
  2. Poi prendere quella lista di URL e raschiare i dati che stai cercando, e poi incollarla in un data.frame.

Quindi, ecco qui ...

library(RCurl)

### 1) First task is to get all of the web links we will need ##
base_url<-"http://gtrnadb.ucsc.edu/"
base_html<-getURLContent(base_url)[[1]]
links<-strsplit(base_html,"a href=")[[1]]

get_data_url<-function(s) {
    u_split1<-strsplit(s,"/")[[1]][1]
    u_split2<-strsplit(u_split1,'\\"')[[1]][2]
    ifelse(grep("[[:upper:]]",u_split2)==1 & length(strsplit(u_split2,"#")[[1]])<2,return(u_split2),return(NA))
}

# Extract only those element that are relevant
genomes<-unlist(lapply(links,get_data_url))
genomes<-genomes[which(is.na(genomes)==FALSE)]

### 2) Now, scrape the genome data from all of those URLS ###

# This requires two complementary functions that are designed specifically
# for the UCSC website. The first parses the data from a -structs.html page
# and the second collects that data in to a multi-dimensional list
parse_genomes<-function(g) {
    g_split1<-strsplit(g,"\n")[[1]]
    g_split1<-g_split1[2:5]
    # Pull all of the data and stick it in a list
    g_split2<-strsplit(g_split1[1],"\t")[[1]]
    ID<-g_split2[1]                             # Sequence ID
    LEN<-strsplit(g_split2[2],": ")[[1]][2]     # Length
    g_split3<-strsplit(g_split1[2],"\t")[[1]]
    TYPE<-strsplit(g_split3[1],": ")[[1]][2]    # Type
    AC<-strsplit(g_split3[2],": ")[[1]][2]      # Anticodon
    SEQ<-strsplit(g_split1[3],": ")[[1]][2]     # ID
    STR<-strsplit(g_split1[4],": ")[[1]][2]     # String
    return(c(ID,LEN,TYPE,AC,SEQ,STR))
}

# This will be a high dimensional list with all of the data, you can then manipulate as you like
get_structs<-function(u) {
    struct_url<-paste(base_url,u,"/",u,"-structs.html",sep="")
    raw_data<-getURLContent(struct_url)
    s_split1<-strsplit(raw_data,"<PRE>")[[1]]
    all_data<-s_split1[seq(3,length(s_split1))]
    data_list<-lapply(all_data,parse_genomes)
    for (d in 1:length(data_list)) {data_list[[d]]<-append(data_list[[d]],u)}
    return(data_list)
}

# Collect data, manipulate, and create data frame (with slight cleaning)
genomes_list<-lapply(genomes[1:2],get_structs) # Limit to the first two genomes (Bdist & Spurp), a full scrape will take a LONG time
genomes_rows<-unlist(genomes_list,recursive=FALSE) # The recursive=FALSE saves a lot of work, now we can just do a straigh forward manipulation
genome_data<-t(sapply(genomes_rows,rbind))
colnames(genome_data)<-c("ID","LEN","TYPE","AC","SEQ","STR","NAME")
genome_data<-as.data.frame(genome_data)
genome_data<-subset(genome_data,ID!="</PRE>")   # Some malformed web pages produce bad rows, but we can remove them

head(genome_data)

Il frame di dati risultante contiene sette colonne relative a ciascun genoma: ID, lunghezza, tipo, sequenza, stringa, e il nome. La colonna Nome contiene il genoma di base, che era la mia ipotesi migliore per l'organizzazione dei dati. Qui quello che sembra:

head(genome_data)
                                   ID   LEN TYPE                           AC                                                                       SEQ
1     Scaffold17302.trna1 (1426-1498) 73 bp  Ala     AGC at 34-36 (1459-1461) AGGGAGCTAGCTCAGATGGTAGAGCGCTCGCTTAGCATGCGAGAGGtACCGGGATCGATGCCCGGGTTTTCCA
2   Scaffold20851.trna5 (43038-43110) 73 bp  Ala   AGC at 34-36 (43071-43073) AGGGAGCTAGCTCAGATGGTAGAGCGCTCGCTTAGCATGCGAGAGGtACCGGGATCGATGCCCGGGTTCTCCA
3   Scaffold20851.trna8 (45975-46047) 73 bp  Ala   AGC at 34-36 (46008-46010) TGGGAGCTAGCTCAGATGGTAGAGCGCTCGCTTAGCATGCGAGAGGtACCGGGATCGATGCCCGGGTTCTCCA
4     Scaffold17302.trna2 (2514-2586) 73 bp  Ala     AGC at 34-36 (2547-2549) GGGGAGCTAGCTCAGATGGTAGAGCGCTCGCTTAGCATGCGAGAGGtACAGGGATCGATGCCCGGGTTCTCCA
5 Scaffold51754.trna5 (253637-253565) 73 bp  Ala AGC at 34-36 (253604-253602) CGGGGGCTAGCTCAGATGGTAGAGCGCTCGCTTAGCATGCGAGAGGtACCGGGATCGATGCCCGGGTCCTCCA
6     Scaffold17302.trna4 (6027-6099) 73 bp  Ala     AGC at 34-36 (6060-6062) GGGGAGCTAGCTCAGATGGTAGAGCGCTCGCTTAGCATGCGAGAGGtACCGGGATCGATGCCCGAGTTCTCCA
                                                                        STR  NAME
1 .>>>>>>..>>>>........<<<<.>>>>>.......<<<<<.....>>>>>.......<<<<<<<<<<<.. Spurp
2 .>>>>>>..>>>>........<<<<.>>>>>.......<<<<<.....>>>>>.......<<<<<<<<<<<.. Spurp
3 .>>>>>>..>>>>........<<<<.>>>>>.......<<<<<.....>>>>>.......<<<<<<<<<<<.. Spurp
4 >>>>>>>..>>>>........<<<<.>>>>>.......<<<<<.....>.>>>.......<<<.<<<<<<<<. Spurp
5 .>>>>>>..>>>>........<<<<.>>>>>.......<<<<<.....>>>>>.......<<<<<<<<<<<.. Spurp
6 >>>>>>>..>>>>........<<<<.>>>>>.......<<<<<......>>>>.......<<<<.<<<<<<<. Spurp

Spero che questo aiuta, e grazie per la piccola sfida pomeriggio R divertimento Domenica!

Altri suggerimenti

Appena provato usando Mozenda ( http://www.mozenda.com ). Dopo circa 10 minuti e ho avuto un agente in grado di raschiare i dati come si descrive. Si può essere in grado di ottenere tutti questi dati usando solo la loro versione di prova gratuita. Coding è divertente, se avete tempo, ma sembra che si può già avere una soluzione in codice per voi. Bel lavoro Drew.

problema interessante e concordano sul fatto che R è fresco, ma in qualche modo trovo R di essere un po 'ingombrante in questo senso. Mi sembrano preferire per ottenere i dati in forma di testo intermedio prima in modo da essere in grado di verificare che i dati siano corretti in ogni passo ... Se i dati è pronto nella sua forma finale o per il caricamento dei dati da qualche parte RCurl è molto utile.

più semplice, a mio parere sarebbe quello di (su linux / unix / mac / o in Cygwin) proprio rispecchiare l'intera http : sito //gtrnadb.ucsc.edu/ (usando wget) e prendere i file denominati / -structs.html, sed o awk i dati che si desidera e formattarlo per la lettura in R.

Sono sicuro che ci sarebbero un sacco di altri modi anche.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top