Cross recurrewnce analysis can be used to study synchronisation and coupling direction. There are other several orther packages and software that can run (C)RQA:
crqa
by Coco & Dale (2014) gives a good introduction and of RQA and CRQA: https://www.frontiersin.org/articles/10.3389/fpsyg.2014.00510/fullIn 2008 there was some commotion about a speech held by Barack Obama in Milwaukee (news item). According to the media the speech was very similar to a speech held the gouverneur of Massachusetts (Deval Patrick) some years earlier. Here are some fragments of the speeches,
Obama (2008):
Don’t tell me words don’t matter. “I have a dream.” Just words? “We hold these truths to be self-evident, that all men are created equal.” Just words? “We have nothing to fear but fear itself”—just words? Just speeches?
Patrick (2006):
“We hold these truths to be self-evident, that all men are created equal.” Just words—just words! “We have nothing to fear but fear itself.” Just words! “Ask not what your country can do for you, ask what you can do for your country.” Just words! “I have a dream.” Just words!
# Load the speeches as timeseries
library(casnet)
obama2008 <- strsplit(x = "dont tell me words dont matter I have a dream just words we hold these truths to be selfevident that all men are created equal just words We have nothing to fear but fear itself just words just speeches", split = " ")[[1]]
patrick2006 <- strsplit(x = "we hold these truths to be selfevident that all men are created equal just words just words we have nothing to fear but fear itself just words ask not what your country can do for you ask what you can do for your country just words I have a dream just words", split = " ")[[1]]
uniqueID <- as.numeric_discrete(c(obama2008,patrick2006))
speeches <- as.data.frame(ts_trimfill(x=uniqueID[1:length(obama2008)], y=uniqueID[(length(obama2008)+1):length(uniqueID)]))
colnames(speeches) <- c("Obama","Patrick")
Plot both time series.
0
rp()
.emLag
, emDim
and emRad
rp()
(ignore the warning),rp_plot()
rp_diagProfile()
What is your opinion about the similarity of these speeches?
-2
, or 0
), but not the other makes sure that value will not be recurring in a Cross Recurrence Plot.# Plot the speech series
plot(ts(speeches))
# Cross recurrence matrix
RM <- rp(y1 = as.numeric_discrete(speeches$Obama),
y2 = as.numeric_discrete(speeches$Patrick), emDim = 1, emLag = 1, emRad = 0)
# Measures
crqa_out <- rp_measures(RM, silent = FALSE)
##
## ~~~o~~o~~casnet~~o~~o~~~
##
## Global Measures
## Global Max.rec.points N.rec.points Recurrence.Rate Singular.points
## 1 Recurrence Matrix 2652 71 0.0262574 15
## Divergence Repetitiveness Anisotropy
## 1 0.06666667 0 NA
##
##
## Line-based Measures
## Line.based N.lines N.points.on.lines Measure Rate Mean Max
## 1 Diagonal 15 56 Determinism 0.7887324 3.733333 15
## 2 Vertical 0 0 V Laminarity 0.0000000 NaN -Inf
## 3 Horizontal 0 0 H Laminarity 0.0000000 NaN -Inf
## Entropy.of.lengths Relative.entropy CoV.of.lengths
## 1 1.080574 0.2748275 0.9891909
## 2 0.000000 0.0000000 NA
## 3 0.000000 0.0000000 NA
##
## ~~~o~~o~~casnet~~o~~o~~~
# Diagonal profile --> The plot function is a bit broken, here we make our plot
drp <- rp_diagProfile(RM, diagWin = 40, doShuffle = FALSE, doPlot = FALSE)
##
## Profile 1
library(rio)
y1 <- sin(1:500*2*pi/67)
y2 <- sin(.01*(1:500*2*pi/67)^2)
# Here are the circle trace data
xy <- import("https://raw.githubusercontent.com/FredHasselman/The-Complex-Systems-Approach-Book/master/assignments/assignment_data/RQA_circletrace/mouse_circle_xy.csv")
circle_x <- xy$x[1:500]
circle_y <- xy$y[1:500]
Find a common embedding delay and an embedding dimension (if you calculate an embedding dimension for each signal separately, as a rule of thumb use the highest embedding dimension you find in further analyses).
rp()
rp_cl()
using th time series as input, or rp()
using a thresholded matrix as input.
casnet
manual for function est_radius()
.rp_plot()
will call est_radius()
if no radius is provided in the argument emRad
.di2bi()
,Produce a plot of the recurrence matrix using rp_plot()
. Look at the manual pages.
rp_diagProfile()
. More elaborate explanation can be found in Coco & Dale (2014).
rp_diagProfile(RM, winDiag = , ...)
. Where winDiag
is will indicate the window size -winDiag ... 0 ... +winDiag
.rp_diagProfile()
can do a shuffled analysis, check the manual pages.Nshuffle = 1
(or wait a long time)NOTE: If you generate surrogate timeseries, make sure the RR is the same for all surrogates. Try to keep the RR in the same range by using.
library(rio)
y1 <- sin(1:1000*2*pi/67)
y2 <- sin(.01*(1:1000*2*pi/67)^2)
# Time series
plot(cbind(ts(y1),ts(y2)))
The diagnostic plot of the sine wave
y1
looks a bit odd. This is due to the fact that mutual information will discretize the time series, and the sine will fill all bins with the same values, because it is perfectly repeating itself. We’ll use emDim = 2 and lag = 1
emLag <- 1
emDim <- 2
RM <- rp(y1=y1, y2=y2,emDim = emDim, emLag = emLag)
# Unthresholded Matrix
rp_plot(RM, plotDimensions = TRUE)
# Thresholded Matrix, based on 5% RR
emRad <- est_radius(RM = RM, targetValue = .05)$Radius
RP <- di2bi(RM, emRad = emRad)
rp_plot(RP, plotDimensions = TRUE)
# The diagonal profile
drp <- rp_diagProfile(RP, diagWin = 50, doPlot = FALSE)
library(ggplot2)
ggplot(drp, aes(x = as.numeric_discrete(labels), y = RR, colour = variable)) +
geom_line() + theme_bw()
# Compare CRQA with one randomly shuffled series: broken...
# drpRND <- rp_diagProfile(RP, diagWin = 50, doShuffle = TRUE, y1 = y1, y2 = y2, Nshuffle = 19, doPlot = FALSE)
# Here are the circle trace data
xy <- import("https://raw.githubusercontent.com/FredHasselman/The-Complex-Systems-Approach-Book/master/assignments/assignment_data/RQA_circletrace/mouse_circle_xy.csv")
circle_x <- xy$x[1:1000]
circle_y <- xy$y[1:1000]
# Time Series
plot(cbind(ts(circle_x),ts(circle_y)))
The circle trace data can be embedded in 3 dimensions. This is not so strange, even though the circle was drawn in 2 dimensions, there are also speed/acceleration and accuracy constraints.
emLag <- median(params_cx$optimLag, params_cy$optimLag)
emDim <- max(params_cx$optimDim, params_cy$optimDim)
RM <- rp(y1=circle_x, y2=circle_y,emDim = emDim, emLag = emLag)
# Unthresholded Matrix
rp_plot(RM, plotDimensions = TRUE)
##
## Searching for a radius that will yield 0.05 for RR
##
## Converged! Found an appropriate radius...
##
## Profile 1