2011-01-13 17 views
7

Say Ho la seguente matrice:calcolare una media giornaliera R

x1 = 1:288 
x2 = matrix(x1,nrow=96,ncol=3) 

C'è un modo semplice per ottenere la media di righe 1: 24,25: 48,49: 72,73: 96 per colonna 2?

Fondamentalmente ho una serie storica di un anno e devo fare una media dei dati ogni 24 ore.

risposta

8

C'è.

Supponiamo di avere i giorni:

Days <- rep(1:4,each=24) 

si poteva fare facilmente

tapply(x2[,2],Days,mean) 

Se si dispone di un dataframe con una variabile data, è possibile utilizzare quello. Si può fare per tutte le variabili in una sola volta, utilizzando aggregati:

x2 <- as.data.frame(cbind(x2,Days)) 
aggregate(x2[,1:3],by=list(Days),mean) 

Date un'occhiata ai file di aiuto di queste funzioni per iniziare. Anche fare una ricerca qui, ci sono abbastanza alcune altre risposte interessanti su questo problema:

PS: Se avete intenzione di fare un sacco di timeseries, si dovrebbe dare un'occhiata al pacchetto zoo (su CRAN: http://cran.r-project.org/web/packages/zoo/index.html)

+0

@SnowFrog Ti sbagli. tapply non crea un frame di dati. Crea un vettore (in questo caso). Grande differenza. –

+0

Un problema con il metodo 'tapply' è che crea un vettore (numero di colonne = numero di giorni).Il metodo 'aggregate' crea un frame di dati (1 colonna con numero di righe = numero di giorni), che può essere più pratico se è necessaria una successiva manipolazione dei dati. – SnowFrog

2

Il modo compatto e computazionalmente veloce per farlo è quello di rimodellare il vettore in una matrice adeguata e calcolare la colonna ans.

colMeans(matrix(x2[,2],nrow=24)) 
+0

soluzione pulita, a condizione che non ci siano dati mancanti da nessuna parte. Altrimenti la matrice non rappresenterebbe i giorni. –

+0

È necessario fare attenzione con questo metodo in modo che le dimensioni siano corrette. Ma puoi gestire i dati mancanti usando NA per quelli e usando na.rm = TRUE –

+0

Ne sono consapevole :-) Voglio dire che manca nel senso di "non ogni giorno ha 24 righe di dati" –

4

1) ts. Trattandosi di una serie temporale intervalli regolari, convertirlo in una serie ts e poi aggregare dalla frequenza 24 a frequenza 1:

> aggregate(ts(x2[, 2], freq = 24), 1, mean) 

dando:

Time Series: 
Start = 1 
End = 4 
Frequency = 1 
[1] 108.5 132.5 156.5 180.5 

2) zoo. Qui sta usando lo zoo. Il pacchetto zoo può anche gestire serie spaziate in modo irregolare (se avessimo bisogno di estenderlo). Sotto day.hour è il numero del giorno (1, 2, 3, 4) più l'ora come una frazione del giorno in modo che floor(day.hour) è solo il numero del giorno:

> library(zoo) 
> day.hour <- seq(1, length = length(x2[, 2]), by = 1/24) 
> z <- zoo(x2[, 2], day.hour) 
> aggregate(z, floor, mean) 
    1  2  3  4 
108.5 132.5 156.5 180.5 

Se zz è l'uscita poi coredata(zz) e time(zz) sono i valori e le volte, rispettivamente, come vettori ordinari.

+0

+1 per mostrare come usare zoo e ts per quello. Non l'ho menzionato perché non volevo dare troppa importanza ai dati nel vero problema, ma è sicuramente pertinente e utile. –

Problemi correlati