Come generare dati binari di serie temporali con correlazione automatica casuale?


15

Come posso generare serie temporali binarie tali che:

  1. È specificata la probabilità media di osservare 1 (diciamo 5%);
  2. Probabilità condizionale di osservare 1 alla volta dato il valore a (diciamo il 30% se il valore era 1)?tt1t1

Risposte:


17

Utilizzare una catena Markov a due stati.

Se gli stati sono chiamati 0 e 1, la catena può essere rappresentata da una matrice 2x2 che fornisce le probabilità di transizione tra stati, dove è la probabilità di spostarsi dallo stato allo stato . In questa matrice, ogni riga dovrebbe essere 1.0.PPijij

Dall'istruzione 2, abbiamo e la semplice conservazione quindi dice .P11=0.3P10=0.7

Dall'istruzione 1, si desidera che la probabilità a lungo termine (chiamata anche equilibrio o stato stazionario) sia . Questo dice risoluzione dà e una matrice di transizioneP1=0.05

P1=0.05=0.3P1+P01(1P1)
P01=0.0368421
P=(0.9631580.03684210.70.3)

(Puoi verificare la correttezza della tua matrice di transizione elevandola a una potenza elevata - in questo caso 14 fa il lavoro - ogni riga del risultato fornisce le stesse identiche probabilità di stato stazionario)

Ora nel tuo programma di numeri casuali, inizia scegliendo casualmente lo stato 0 o 1; questo seleziona quale riga di stai usando. Quindi utilizzare un numero casuale uniforme per determinare lo stato successivo. Sputare quel numero, risciacquare, ripetere se necessario.P


Soluzione interessante! Hai forse qualche codice di esempio in R? Antone altro?
user333

@Mike Puoi per favore registrare il tuo account? Sei un utente piuttosto attivo e dobbiamo unirlo ripetutamente manualmente. Il processo è abbastanza semplice; visita stats.stackexchange.com/login

Grazie. Come posso stimare la catena di Markov (matrice di transizione) dati i dati? Esiste una funzione R per farlo?
user333,

6

Mi sono preso una brutta pausa nel scrivere la risposta di @Mike Anderson in R. Non riuscivo a capire come farlo usando sapply, quindi ho usato un loop. Ho cambiato leggermente i probi per ottenere un risultato più interessante e ho usato 'A' e 'B' per rappresentare gli stati. Fatemi sapere cosa ne pensate.

set.seed(1234)
TransitionMatrix <- data.frame(A=c(0.9,0.7),B=c(0.1,0.3),row.names=c('A','B'))
Series <- c('A',rep(NA,99))
i <- 2
while (i <= length(Series)) {
    Series[i] <- ifelse(TransitionMatrix[Series[i-1],'A']>=runif(1),'A','B')
    i <- i+1
}
Series <- ifelse(Series=='A',1,0)
> Series
  [1] 1 1 1 1 1 1 1 1 1 1 1 1 1 1 0 1 1 1 1 1 1 1 1 1 1 1 1 1 0 0 1 1 1 1 1 1 1
 [38] 1 1 0 0 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1
 [75] 1 1 1 1 1 1 1 0 1 1 1 1 1 1 1 1 1 1 0 1 1 1 1 1 1 1

/ modifica: in risposta al commento di Paul, ecco una formulazione più elegante

set.seed(1234)

createSeries <- function(n, TransitionMatrix){
  stopifnot(is.matrix(TransitionMatrix))
  stopifnot(n>0)

  Series <- c(1,rep(NA,n-1))
  random <- runif(n-1)
  for (i in 2:length(Series)){
    Series[i] <- TransitionMatrix[Series[i-1]+1,1] >= random[i-1]
  }

  return(Series)
}

createSeries(100, matrix(c(0.9,0.7,0.1,0.3), ncol=2))

Ho scritto il codice originale quando stavo solo imparando R, quindi tagliami un po 'di gioco. ;-)

Ecco come valuteresti la matrice di transizione, date le serie:

Series <- createSeries(100000, matrix(c(0.9,0.7,0.1,0.3), ncol=2))
estimateTransMatrix <- function(Series){
  require(quantmod)
  out <- table(Lag(Series), Series)
  return(out/rowSums(out))
}
estimateTransMatrix(Series)

   Series
            0         1
  0 0.1005085 0.8994915
  1 0.2994029 0.7005971

L'ordine viene scambiato rispetto alla mia matrice di transizione originale, ma ottiene le giuste probabilità.


Grande! Sarò appena pissible ... Sembra abbastanza buono ....
user333

È possibile fare l'inverso? Vista la serie stimare la matrice?
user333,

Pr(Xt=i|Xt1=j)

+1, ma ho anche alcuni commenti: un forloop sarebbe un po 'più pulito qui, sai la lunghezza di Series, quindi basta usare for(i in 2:length(Series)). Questo elimina la necessità di i = i + 1. Inoltre, perché prima campionare Ae poi convertirlo in 0,1? È possibile campionare direttamente 0"e 1".
Paul Hiemstra,

2
Più in generale, è possibile quindi inserirlo in una nuova funzione createAutocorBinSeries = function(n=100,mean=0.5,corr=0) { p01=corr*(1-mean)/mean createSeries(n,matrix(c(1-p01,p01,corr,1-corr),nrow=2,byrow=T)) };createAutocorBinSeries(n=100,mean=0.5,corr=0.9);createAutocorBinSeries(n=100,mean=0.5,corr=0.1);per consentire l'autocorrelazione arbitraria e predefinita del ritardo 1
Tom Wenseleers,

1

Ecco una risposta basata sul markovchainpacchetto che può essere generalizzato a strutture di dipendenza più complesse.

library(markovchain)
library(dplyr)

# define the states
states_excitation = c("steady", "excited")

# transition probability matrix
tpm_excitation = matrix(
  data = c(0.2, 0.8, 0.2, 0.8), 
  byrow = TRUE, 
  nrow = 2,
  dimnames = list(states_excitation, states_excitation)
)

# markovchain object
mc_excitation = new(
  "markovchain",
  states = states_excitation,
  transitionMatrix = tpm_excitation,
  name = "Excitation Transition Model"
)

# simulate
df_excitation = data_frame(
  datetime = seq.POSIXt(as.POSIXct("01-01-2016 00:00:00", 
                                   format = "%d-%m-%Y %H:%M:%S", 
                                   tz = "UTC"), 
                        as.POSIXct("01-01-2016 23:59:00", 
                                   format = "%d-%m-%Y %H:%M:%S", 
                                   tz = "UTC"), by = "min"),
  excitation = rmarkovchain(n = 1440, mc_excitation))

# plot
df_excitation %>% 
  ggplot(aes(x = datetime, y = as.numeric(factor(excitation)))) + 
  geom_step(stat = "identity") + 
  theme_bw() + 
  scale_y_discrete(name = "State", breaks = c(1, 2), 
                   labels = states_excitation)

Questo ti dà:

inserisci qui la descrizione dell'immagine


0

Ho perso la traccia del documento in cui è stato descritto questo approccio, ma qui va.

Decomporre la matrice di transizione in

T=(1pt)[1001]+pt[p0p0(1p0)(1p0)]=(1pt)I+ptE

1ptptp0

ptT11T11=(1pt)+pt(1p0)

Una delle caratteristiche utili di questa decomposizione è che si generalizza abbastanza facilmente alla classe di modelli di Markov correlati in problemi dimensionali superiori.


Se qualcuno ha visto il documento che sviluppa questa rappresentazione, per favore fatemelo sapere.
Dave,
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.