In this topic we will explore temporal data in R in order to visualize the temporal aspect of porpoise distribution.

1. Dealing with time variables in R

As discussed previously, a variable is recognized as time in the POSIxct data type, for example by applying lubridate::parse_date_time().

A first step is to plot the value of interest against time.

ggplot(data = poddata_day, aes(x = Time, y = Dpm)) + 
  theme_bw() +
  theme(axis.text = element_text(size = 16),
        axis.title.x = element_blank()) +
  geom_point() + geom_line()

More relevant is plotting the time series for each zone seperately. This can be done with facet_wrap() or by making a list of plots.

ggplot(data = poddata_day, aes(x = Time, y = Dpm)) + 
  theme_bw() +
  theme(axis.text = element_text(size = 16),
        axis.title.x = element_blank()) +
  geom_point() + geom_line() + facet_wrap(~Zone, nrow = length(unique(poddata$Station)))

lapply(unique(poddata_day$Zone), function(x){
  ggplot(data = poddata_day[poddata_day$Zone == x,], aes(x = Time, y = Dpm)) + 
    theme_bw() +
    theme(axis.text = element_text(size = 16),
          axis.title.x = element_blank()) +
    geom_point() + geom_line() + ggtitle(x)
})
[[1]]

[[2]]

[[3]]

[[4]]

[[5]]

[[6]]

[[7]]

[[8]]

[[9]]

[[10]]

Same can be done for different deployments.

lapply(unique(poddata_day$Deployment_fk), function(x){
  ggplot(data = poddata_day[poddata_day$Deployment_fk == x,], aes(x = Time, y = Dpm)) + 
    theme_bw() +
    theme(axis.text = element_text(size = 16),
          axis.title.x = element_blank()) +
    geom_point() + geom_line() + ggtitle(x)
})

2. Autocorrelation

R provides a very easy function to investigate the autocorrelation in your data: acf.

poddata_day <- arrange(poddata_day, Zone, Time)
acf(poddata_day$Dpm)

Again, we are interested in the autocorrelation of each Zone seperately.

par(mfrow=c(2,2)) # see four plots at a time
lapply(unique(poddata_day$Zone), function(x) {
  data <- acf(poddata_day[poddata_day$Zone == x,]$Dpm, plot = F)
  plot(data, main = x)
})
[[1]]
NULL

[[2]]
NULL

[[3]]
NULL

[[4]]
NULL

[[5]]
NULL

[[6]]
NULL

[[7]]
NULL

[[8]]
NULL

[[9]]
NULL

[[10]]
NULL

We can also take these values and combine them in one plot.

lacf <- lapply(unique(poddata_day$Zone), function(x){
  o <- filter(poddata_day, Zone == x)
  oa <- acf(o$Dpm)
  dfo <- data.frame(acf = oa$acf[,,1], lag = oa$lag[,,1], Zone = x)
})
library(plyr) # Now we use the package plyr to make a dataframe out of our list
dacf <- ldply(lacf, rbind)
ggplot(dacf) + geom_path(aes(x=lag, y=acf, group=Zone))

3. Smoothing

The goal of smoothing is generally to aid visual interpretation of a time series. Let’s try on two subsets of our data.

test1 <- filter(poddata_day, Deployment_fk == 2578)
test2 <- filter(poddata_day, Deployment_fk == 2585)

Applying geom_smooth() plots a loess smoother (weighted regression) on the series.

ggplot(data = test1, aes(x = Time, y = Dpm)) + 
  geom_point() + geom_line() + geom_smooth() + ggtitle(2578)

ggplot(data = test2, aes(x = Time, y = Dpm)) + 
  geom_point() + geom_line() + geom_smooth() + ggtitle(2585)

Another way to smooth data, is to calculate a moving average.

acf(test1$Dpm) # First, we check the autocorrelation to choose our window size.

library(pastecs)
Loading required package: boot

Attaching package: <U+393C><U+3E31>pastecs<U+393C><U+3E32>

The following objects are masked from <U+393C><U+3E31>package:dplyr<U+393C><U+3E32>:

    first, last
movavg <- decaverage(test1$Dpm, order = 3) # By choosing an order of 3, a window size of 7 will be obtained (3 values to the left, 3 to the right).
movavg # movavg is a list
 Call:
 decaverage(x = test1$Dpm, order = 3)

Components
[1] "filtered"  "residuals"
plot(movavg)

Now in ggplot:

test1$decavg <- data.frame(movavg$series)$filtered
ggplot(test1, aes(x = Time, y = Dpm)) + geom_point() + geom_line() + 
  geom_path(aes(y = decavg), size= 1.2, colour = "red")

movavg <- decaverage(test1$Dpm, order = 3, times = 5)
test1$decavg <- data.frame(movavg$series)$filtered
ggplot(test1, aes(x = Time, y = Dpm)) + geom_point() + geom_line() + 
  geom_path(aes(y = decavg), size= 1.2, colour = "red")

Now, we can do the same for the other subset.

acf(test2$Dpm)

movavg <- decaverage(test2$Dpm, order = 1, times = 5)
test2$decavg <- data.frame(movavg$series)$filtered
ggplot(test2, aes(x = Time, y = Dpm)) + geom_point() + geom_line() + 
  geom_path(aes(y = decavg), size= 1.2, colour = "red")

Discussion: which smoothing technique is preferred? Is smoothing necessary?

LS0tDQp0aXRsZTogIkMtUE9EIGRhdGEgd29ya3Nob3A6IFRpbWUgc2VyaWVzIg0KYXV0aG9yOiAiVkxJWiAtIEZsYW5kZXJzIE1hcmluZSBJbnN0aXR1dGUiDQpkYXRlOiAiT2N0b2JlciA1LTYsIDIwMTciDQpvdXRwdXQ6IGh0bWxfbm90ZWJvb2sNCi0tLQ0KDQpJbiB0aGlzIHRvcGljIHdlIHdpbGwgZXhwbG9yZSB0ZW1wb3JhbCBkYXRhIGluIFIgaW4gb3JkZXIgdG8gdmlzdWFsaXplIHRoZSB0ZW1wb3JhbCBhc3BlY3Qgb2YgcG9ycG9pc2UgZGlzdHJpYnV0aW9uLg0KDQojIyAxLiBEZWFsaW5nIHdpdGggdGltZSB2YXJpYWJsZXMgaW4gUg0KQXMgZGlzY3Vzc2VkIHByZXZpb3VzbHksIGEgdmFyaWFibGUgaXMgcmVjb2duaXplZCBhcyB0aW1lIGluIHRoZSBQT1NJeGN0IGRhdGEgdHlwZSwgZm9yIGV4YW1wbGUgYnkgYXBwbHlpbmcgKipsdWJyaWRhdGU6OnBhcnNlX2RhdGVfdGltZSgpKiouDQoNCkEgZmlyc3Qgc3RlcCBpcyB0byBwbG90IHRoZSB2YWx1ZSBvZiBpbnRlcmVzdCBhZ2FpbnN0IHRpbWUuDQpgYGB7cn0NCmdncGxvdChkYXRhID0gcG9kZGF0YV9kYXksIGFlcyh4ID0gVGltZSwgeSA9IERwbSkpICsgDQogIHRoZW1lX2J3KCkgKw0KICB0aGVtZShheGlzLnRleHQgPSBlbGVtZW50X3RleHQoc2l6ZSA9IDE2KSwNCiAgICAgICAgYXhpcy50aXRsZS54ID0gZWxlbWVudF9ibGFuaygpKSArDQogIGdlb21fcG9pbnQoKSArIGdlb21fbGluZSgpDQpgYGANCmBgYHtyfQ0KZ2dwbG90KGRhdGEgPSBwb2RkYXRhX2RheSwgYWVzKHggPSBUaW1lLCB5ID0gRHBtKSkgKyANCiAgdGhlbWVfYncoKSArDQogIHRoZW1lKGF4aXMudGV4dCA9IGVsZW1lbnRfdGV4dChzaXplID0gMTYpLA0KICAgICAgICBheGlzLnRpdGxlLnggPSBlbGVtZW50X2JsYW5rKCkpICsNCiAgZ2VvbV9wb2ludCgpICsgZ2VvbV9saW5lKCkNCmBgYA0KDQpNb3JlIHJlbGV2YW50IGlzIHBsb3R0aW5nIHRoZSB0aW1lIHNlcmllcyBmb3IgZWFjaCB6b25lIHNlcGVyYXRlbHkuIFRoaXMgY2FuIGJlIGRvbmUgd2l0aCAqKmZhY2V0X3dyYXAoKSoqIG9yIGJ5IG1ha2luZyBhIGxpc3Qgb2YgcGxvdHMuDQpgYGB7cn0NCmdncGxvdChkYXRhID0gcG9kZGF0YV9kYXksIGFlcyh4ID0gVGltZSwgeSA9IERwbSkpICsgDQogIHRoZW1lX2J3KCkgKw0KICB0aGVtZShheGlzLnRleHQgPSBlbGVtZW50X3RleHQoc2l6ZSA9IDE2KSwNCiAgICAgICAgYXhpcy50aXRsZS54ID0gZWxlbWVudF9ibGFuaygpKSArDQogIGdlb21fcG9pbnQoKSArIGdlb21fbGluZSgpICsgZmFjZXRfd3JhcCh+Wm9uZSwgbnJvdyA9IGxlbmd0aCh1bmlxdWUocG9kZGF0YSRTdGF0aW9uKSkpDQpgYGANCmBgYHtyfQ0KZ2dwbG90KGRhdGEgPSBwb2RkYXRhX2RheSwgYWVzKHggPSBUaW1lLCB5ID0gRHBtKSkgKyANCiAgdGhlbWVfYncoKSArDQogIHRoZW1lKGF4aXMudGV4dCA9IGVsZW1lbnRfdGV4dChzaXplID0gMTYpLA0KICAgICAgICBheGlzLnRpdGxlLnggPSBlbGVtZW50X2JsYW5rKCkpICsNCiAgZ2VvbV9wb2ludCgpICsgZ2VvbV9saW5lKCkgKyBmYWNldF93cmFwKH5ab25lLCBucm93ID0gbGVuZ3RoKHVuaXF1ZShwb2RkYXRhJFN0YXRpb24pKSkNCmBgYA0KDQpgYGB7cn0NCmxhcHBseSh1bmlxdWUocG9kZGF0YV9kYXkkWm9uZSksIGZ1bmN0aW9uKHgpew0KICBnZ3Bsb3QoZGF0YSA9IHBvZGRhdGFfZGF5W3BvZGRhdGFfZGF5JFpvbmUgPT0geCxdLCBhZXMoeCA9IFRpbWUsIHkgPSBEcG0pKSArIA0KICAgIHRoZW1lX2J3KCkgKw0KICAgIHRoZW1lKGF4aXMudGV4dCA9IGVsZW1lbnRfdGV4dChzaXplID0gMTYpLA0KICAgICAgICAgIGF4aXMudGl0bGUueCA9IGVsZW1lbnRfYmxhbmsoKSkgKw0KICAgIGdlb21fcG9pbnQoKSArIGdlb21fbGluZSgpICsgZ2d0aXRsZSh4KQ0KfSkNCmBgYA0KDQpTYW1lIGNhbiBiZSBkb25lIGZvciBkaWZmZXJlbnQgZGVwbG95bWVudHMuDQpgYGB7cn0NCmxhcHBseSh1bmlxdWUocG9kZGF0YV9kYXkkRGVwbG95bWVudF9mayksIGZ1bmN0aW9uKHgpew0KICBnZ3Bsb3QoZGF0YSA9IHBvZGRhdGFfZGF5W3BvZGRhdGFfZGF5JERlcGxveW1lbnRfZmsgPT0geCxdLCBhZXMoeCA9IFRpbWUsIHkgPSBEcG0pKSArIA0KICAgIHRoZW1lX2J3KCkgKw0KICAgIHRoZW1lKGF4aXMudGV4dCA9IGVsZW1lbnRfdGV4dChzaXplID0gMTYpLA0KICAgICAgICAgIGF4aXMudGl0bGUueCA9IGVsZW1lbnRfYmxhbmsoKSkgKw0KICAgIGdlb21fcG9pbnQoKSArIGdlb21fbGluZSgpICsgZ2d0aXRsZSh4KQ0KfSkNCmBgYA0KDQojIyAyLiBBdXRvY29ycmVsYXRpb24NClIgcHJvdmlkZXMgYSB2ZXJ5IGVhc3kgZnVuY3Rpb24gdG8gaW52ZXN0aWdhdGUgdGhlIGF1dG9jb3JyZWxhdGlvbiBpbiB5b3VyIGRhdGE6IGFjZi4NCmBgYHtyfQ0KcG9kZGF0YV9kYXkgPC0gYXJyYW5nZShwb2RkYXRhX2RheSwgWm9uZSwgVGltZSkNCmFjZihwb2RkYXRhX2RheSREcG0pDQpgYGANCmBgYHtyfQ0KYWNmKHBvZGRhdGFfZGF5JERwbSkNCmBgYA0KDQpBZ2Fpbiwgd2UgYXJlIGludGVyZXN0ZWQgaW4gdGhlIGF1dG9jb3JyZWxhdGlvbiBvZiBlYWNoIFpvbmUgc2VwZXJhdGVseS4NCmBgYHtyfQ0KcGFyKG1mcm93PWMoMiwyKSkgIyBzZWUgZm91ciBwbG90cyBhdCBhIHRpbWUNCmxhcHBseSh1bmlxdWUocG9kZGF0YV9kYXkkWm9uZSksIGZ1bmN0aW9uKHgpIHsNCiAgZGF0YSA8LSBhY2YocG9kZGF0YV9kYXlbcG9kZGF0YV9kYXkkWm9uZSA9PSB4LF0kRHBtLCBwbG90ID0gRikNCiAgcGxvdChkYXRhLCBtYWluID0geCkNCn0pDQpgYGANCg0KV2UgY2FuIGFsc28gdGFrZSB0aGVzZSB2YWx1ZXMgYW5kIGNvbWJpbmUgdGhlbSBpbiBvbmUgcGxvdC4NCmBgYHtyfQ0KbGFjZiA8LSBsYXBwbHkodW5pcXVlKHBvZGRhdGFfZGF5JFpvbmUpLCBmdW5jdGlvbih4KXsNCiAgbyA8LSBmaWx0ZXIocG9kZGF0YV9kYXksIFpvbmUgPT0geCkNCiAgb2EgPC0gYWNmKG8kRHBtKQ0KICBkZm8gPC0gZGF0YS5mcmFtZShhY2YgPSBvYSRhY2ZbLCwxXSwgbGFnID0gb2EkbGFnWywsMV0sIFpvbmUgPSB4KQ0KfSkNCmxpYnJhcnkocGx5cikgIyBOb3cgd2UgdXNlIHRoZSBwYWNrYWdlIHBseXIgdG8gbWFrZSBhIGRhdGFmcmFtZSBvdXQgb2Ygb3VyIGxpc3QNCmRhY2YgPC0gbGRwbHkobGFjZiwgcmJpbmQpDQpgYGANCg0KYGBge3J9DQpnZ3Bsb3QoZGFjZikgKyBnZW9tX3BhdGgoYWVzKHg9bGFnLCB5PWFjZiwgZ3JvdXA9Wm9uZSkpDQpgYGANCmBgYHtyfQ0KZ2dwbG90KGRhY2YpICsgZ2VvbV9wYXRoKGFlcyh4PWxhZywgeT1hY2YsIGdyb3VwPVpvbmUpKQ0KYGBgDQoNCiMjIDMuIFNtb290aGluZw0KVGhlIGdvYWwgb2Ygc21vb3RoaW5nIGlzIGdlbmVyYWxseSB0byBhaWQgdmlzdWFsIGludGVycHJldGF0aW9uIG9mIGEgdGltZSBzZXJpZXMuIExldCdzIHRyeSBvbiB0d28gc3Vic2V0cyBvZiBvdXIgZGF0YS4NCmBgYHtyfQ0KdGVzdDEgPC0gZmlsdGVyKHBvZGRhdGFfZGF5LCBEZXBsb3ltZW50X2ZrID09IDI1NzgpDQp0ZXN0MiA8LSBmaWx0ZXIocG9kZGF0YV9kYXksIERlcGxveW1lbnRfZmsgPT0gMjU4NSkNCmBgYA0KDQpBcHBseWluZyBnZW9tX3Ntb290aCgpIHBsb3RzIGEgbG9lc3Mgc21vb3RoZXIgKHdlaWdodGVkIHJlZ3Jlc3Npb24pIG9uIHRoZSBzZXJpZXMuDQpgYGB7cn0NCmdncGxvdChkYXRhID0gdGVzdDEsIGFlcyh4ID0gVGltZSwgeSA9IERwbSkpICsgDQogIGdlb21fcG9pbnQoKSArIGdlb21fbGluZSgpICsgZ2VvbV9zbW9vdGgoKSArIGdndGl0bGUoMjU3OCkNCmBgYA0KYGBge3J9DQpnZ3Bsb3QoZGF0YSA9IHRlc3QxLCBhZXMoeCA9IFRpbWUsIHkgPSBEcG0pKSArIA0KICBnZW9tX3BvaW50KCkgKyBnZW9tX2xpbmUoKSArIGdlb21fc21vb3RoKCkgKyBnZ3RpdGxlKDI1NzgpDQpgYGANCmBgYHtyfQ0KZ2dwbG90KGRhdGEgPSB0ZXN0MiwgYWVzKHggPSBUaW1lLCB5ID0gRHBtKSkgKyANCiAgZ2VvbV9wb2ludCgpICsgZ2VvbV9saW5lKCkgKyBnZW9tX3Ntb290aCgpICsgZ2d0aXRsZSgyNTg1KQ0KYGBgDQpgYGB7cn0NCmdncGxvdChkYXRhID0gdGVzdDIsIGFlcyh4ID0gVGltZSwgeSA9IERwbSkpICsgDQogIGdlb21fcG9pbnQoKSArIGdlb21fbGluZSgpICsgZ2VvbV9zbW9vdGgoKSArIGdndGl0bGUoMjU4NSkNCmBgYA0KDQpBbm90aGVyIHdheSB0byBzbW9vdGggZGF0YSwgaXMgdG8gY2FsY3VsYXRlIGEgbW92aW5nIGF2ZXJhZ2UuIA0KYGBge3J9DQphY2YodGVzdDEkRHBtKSAjIEZpcnN0LCB3ZSBjaGVjayB0aGUgYXV0b2NvcnJlbGF0aW9uIHRvIGNob29zZSBvdXIgd2luZG93IHNpemUuDQpgYGANCmBgYHtyfQ0KYWNmKHRlc3QxJERwbSkgIyBGaXJzdCwgd2UgY2hlY2sgdGhlIGF1dG9jb3JyZWxhdGlvbiB0byBjaG9vc2Ugb3VyIHdpbmRvdyBzaXplLg0KYGBgDQoNCmBgYHtyfQ0KbGlicmFyeShwYXN0ZWNzKQ0KbW92YXZnIDwtIGRlY2F2ZXJhZ2UodGVzdDEkRHBtLCBvcmRlciA9IDMpICMgQnkgY2hvb3NpbmcgYW4gb3JkZXIgb2YgMywgYSB3aW5kb3cgc2l6ZSBvZiA3IHdpbGwgYmUgb2J0YWluZWQgKDMgdmFsdWVzIHRvIHRoZSBsZWZ0LCAzIHRvIHRoZSByaWdodCkuDQptb3ZhdmcgIyBtb3ZhdmcgaXMgYSBsaXN0DQpgYGANCmBgYHtyfQ0KcGxvdChtb3ZhdmcpDQpgYGANCmBgYHtyfQ0KcGxvdChtb3ZhdmcpDQpgYGANCg0KTm93IGluICoqZ2dwbG90Kio6DQpgYGB7cn0NCnRlc3QxJGRlY2F2ZyA8LSBkYXRhLmZyYW1lKG1vdmF2ZyRzZXJpZXMpJGZpbHRlcmVkDQpgYGANCg0KYGBge3J9DQpnZ3Bsb3QodGVzdDEsIGFlcyh4ID0gVGltZSwgeSA9IERwbSkpICsgZ2VvbV9wb2ludCgpICsgZ2VvbV9saW5lKCkgKyANCiAgZ2VvbV9wYXRoKGFlcyh5ID0gZGVjYXZnKSwgc2l6ZT0gMS4yLCBjb2xvdXIgPSAicmVkIikNCmBgYA0KYGBge3J9DQpnZ3Bsb3QodGVzdDEsIGFlcyh4ID0gVGltZSwgeSA9IERwbSkpICsgZ2VvbV9wb2ludCgpICsgZ2VvbV9saW5lKCkgKyANCiAgZ2VvbV9wYXRoKGFlcyh5ID0gZGVjYXZnKSwgc2l6ZT0gMS4yLCBjb2xvdXIgPSAicmVkIikNCmBgYA0KDQpgYGB7cn0NCm1vdmF2ZyA8LSBkZWNhdmVyYWdlKHRlc3QxJERwbSwgb3JkZXIgPSAzLCB0aW1lcyA9IDUpDQp0ZXN0MSRkZWNhdmcgPC0gZGF0YS5mcmFtZShtb3Zhdmckc2VyaWVzKSRmaWx0ZXJlZA0KYGBgDQoNCmBgYHtyfQ0KZ2dwbG90KHRlc3QxLCBhZXMoeCA9IFRpbWUsIHkgPSBEcG0pKSArIGdlb21fcG9pbnQoKSArIGdlb21fbGluZSgpICsgDQogIGdlb21fcGF0aChhZXMoeSA9IGRlY2F2ZyksIHNpemU9IDEuMiwgY29sb3VyID0gInJlZCIpDQpgYGANCmBgYHtyfQ0KZ2dwbG90KHRlc3QxLCBhZXMoeCA9IFRpbWUsIHkgPSBEcG0pKSArIGdlb21fcG9pbnQoKSArIGdlb21fbGluZSgpICsgDQogIGdlb21fcGF0aChhZXMoeSA9IGRlY2F2ZyksIHNpemU9IDEuMiwgY29sb3VyID0gInJlZCIpDQpgYGANCg0KTm93LCB3ZSBjYW4gZG8gdGhlIHNhbWUgZm9yIHRoZSBvdGhlciBzdWJzZXQuDQpgYGB7cn0NCmFjZih0ZXN0MiREcG0pDQpgYGANCmBgYHtyfQ0KYWNmKHRlc3QyJERwbSkNCmBgYA0KDQpgYGB7cn0NCm1vdmF2ZyA8LSBkZWNhdmVyYWdlKHRlc3QyJERwbSwgb3JkZXIgPSAxLCB0aW1lcyA9IDUpDQp0ZXN0MiRkZWNhdmcgPC0gZGF0YS5mcmFtZShtb3Zhdmckc2VyaWVzKSRmaWx0ZXJlZA0KYGBgDQoNCmBgYHtyfQ0KZ2dwbG90KHRlc3QyLCBhZXMoeCA9IFRpbWUsIHkgPSBEcG0pKSArIGdlb21fcG9pbnQoKSArIGdlb21fbGluZSgpICsgDQogIGdlb21fcGF0aChhZXMoeSA9IGRlY2F2ZyksIHNpemU9IDEuMiwgY29sb3VyID0gInJlZCIpDQpgYGANCmBgYHtyfQ0KZ2dwbG90KHRlc3QyLCBhZXMoeCA9IFRpbWUsIHkgPSBEcG0pKSArIGdlb21fcG9pbnQoKSArIGdlb21fbGluZSgpICsgDQogIGdlb21fcGF0aChhZXMoeSA9IGRlY2F2ZyksIHNpemU9IDEuMiwgY29sb3VyID0gInJlZCIpDQpgYGANCg0KRGlzY3Vzc2lvbjogd2hpY2ggc21vb3RoaW5nIHRlY2huaXF1ZSBpcyBwcmVmZXJyZWQ/IElzIHNtb290aGluZyBuZWNlc3Nhcnk/DQo=