Introduction

Before you start

Source

  • The source codes in this example page mostly come from the documents in fdapace.

Sample Example

Load libraries

library(fdapace)
library(dplyr)
library(ggplot2)
library(gridExtra)
library(scales)

Load example data

data("medfly25")

Make Functional pricipal component analysis input

  • IDs : identification
  • tVec : time vector
  • yVec : y vector
Flies <- MakeFPCAInputs(medfly25$ID,medfly25$Days,medfly25$nEggs)

Clustering

  • See also, (FClust)
  • cmethod : ‘EMCluster’ (default), ‘kCFC’
  • default options:
    • methodMuCovEst = “smooth” : method to estimate [cross-sectional(default), smooth]
    • FVEthreshold = 0.90 : fraction-of-variance-explained by the components (0-1)
    • methodBwCov = ‘GCV’ : bandwidth choice method for the smoothed covariance function
    • methodBwMu = ‘GCV’ : bandwidth choice method for the mean function

Chen and Maitra (2015) Chiou and Li (2007)

newClust <- FClust(
  Flies$Ly,Flies$Lt,k=2,
  optnsFPCA = list(
    methodMuCovEst="smooth",
    userBwCov=2,
    FVEthreshold=0.90
  )
)

Observation

After observing data closely, we found that clusters are differentiated by the number of eggs that could be laid. The threshold value may be 25.

veryLowCount = ifelse(
  sapply(unique(medfly25$ID), function(u) 
    sum(medfly25$nEggs[medfly25$ID==u]))>=25,1,2)
veryLowCount
  [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 2 1 1 1 1 1 2 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1
 [48] 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 1 1 1 1 1 1 1 1 1 1 1 1 1 1
 [95] 1 1 1 1 1 1 2 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 2 1 1 1 1 2 1 1 1 1 2 1 1 1 2 2 1 1 1 1 1 1 1 1
[142] 1 2 1 1 2 2 1 1 1 1 1 1 2 1 1 1 1 1 1 1 1 1 1 1 1 1 1 2 1 1 2 1 1 1 1 1 1 1 1 1 1 1 2 2 2 1 1
[189] 1 1 1 2 1 1 1 1 1 1 1 1 1 2 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 2 1 1 1 1 1
[236] 1 1 1 1 1 2 1 1 1 2 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 2 1 1 2 1 1 1 1 1 1 1 1 1 1 1 1 1 1
[283] 1 1 1 1 1 1 1 1 1 1 1 1 2 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 1
[330] 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 2 1 1 2 1 2 1 1 1 1 1 1 1 1 1 1
[377] 1 2 1 1 2 1 1 2 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 2 1 1 1 1 1 1 2 1 1 1 1 1 1 2 1 1 1 1 2
[424] 1 2 1 1 2 1 1 1 1 1 1 2 1 1 1 1 1 1 1 1 2 2 2 1 1 1 2 1 1 1 1 1 1 1 1 1 1 1 1 1 1 2 1 1 1 1 1
[471] 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 2 1 1 1 1 1 1 1 1 1 1 1 1 2
[518] 2 1 1 1 1 1 1 2 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 2 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 2 1 1 1 1
[565] 1 1 1 1 1 1 1 1 1 1 1 2 1 2 1 1 1 2 1 1 1 1 1 1 1 1 1 1 2 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1
[612] 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 2 1 1 1 1 1 1 1 2 1 1 1 1 2 1 1
[659] 1 1 1 2 1 1 1 2 1 2 1 1 1 1 2 1 1 1 1 1 1 1 1 1 2 1 1 1 1 1 1 1 1 1 1 1 1 1 1 2 1 1 1 2 1 1 1
[706] 1 1 1 1 1 1 1 1 1 1 1 1 2 1 2 1 1 2 1 1 1 1 1 1 1 2 1 2 1 1 2 1 1 1 1 1 2 1 1 1 1 1 1 1 1 1 1
[753] 1 2 1 1 1 1 1 1 1 1 1 1 1 2 1 2 1 1 1 1 1 1 2 2 1 1 1 1 1 1 1 1 2 1 1 1 2

Thus, the accuracy is calculated by:

sum((veryLowCount==newClust$cluster))/length(unique(medfly25$ID))
[1] 0.9961977
c1flies <- medfly25[newClust$cluster==1,]
c2flies <- medfly25[newClust$cluster==2,]
c1fliesObj <- MakeFPCAInputs(c1flies$ID,c1flies$Days,c1flies$nEggs)
c2fliesObj <- MakeFPCAInputs(c2flies$ID,c2flies$Days,c2flies$nEggs)
c1fliesFpca <- FPCA(c1fliesObj$Ly,c1fliesObj$Lt,list(methodMuCovEst="smooth"))
plot(c1fliesFpca)

c2fliesFpca <- FPCA(c2fliesObj$Ly,c2fliesObj$Lt,list(methodMuCovEst="smooth"))
plot(c2fliesFpca)

par(mfrow=c(1,2))
CreateModeOfVarPlot(c1fliesFpca,main="Cluster 1")
CreateModeOfVarPlot(c2fliesFpca,main="Cluster 2")
par(mfrow=c(1,1))

LS0tCnRpdGxlOiAiRnVuY3Rpb25hbCBDbHVzdGVyaW5nIgpvdXRwdXQ6IGh0bWxfbm90ZWJvb2sKLS0tCiMgSW50cm9kdWN0aW9uCiogRnVuY3Rpb25hbCBjbHVzdGVyaW5nIGFuYWx5c2lzCiogRXhhbXBsZSBjb2RlcwoqIEF1dGhvcjogVGFla3l1bmcgS2ltIChQaEQuKSwgS3dhbmd3d29uIFVuaXZlcnNpdHksIEtvcmVhCgojIyBCZWZvcmUgeW91IHN0YXJ0CiogQmUgYXdhcmUgdGhhdCB5b3Ugc2hvdWxkIGluc3RhbGwgZ2ZvcnRyYW4gZm9yIE1hYyBPU1guCiogSWYgeW91IGhhdmUgYSBuZXcgTTEgTWFjLCBnbyB0byBodHRwczovL2dpdGh1Yi5jb20vZnhjb3VkZXJ0L2dmb3J0cmFuLWZvci1tYWNPUy9yZWxlYXNlcyB0byBnZXQgYSBuZXcgZ2ZvcnRyYW4gcGFja2FnZS4KKiBZb3UgYWxzbyBuZWVkIHRvIGluc3RhbGwgYEVNQ2x1c3RlcmAgcGFja2FnZSBwcmlvciB0byB1c2UgYEZDbHVzdGAuCgojIyBTb3VyY2UKKiBUaGUgc291cmNlIGNvZGVzIGluIHRoaXMgZXhhbXBsZSBwYWdlIG1vc3RseSBjb21lIGZyb20gdGhlIGRvY3VtZW50cyBpbiBgZmRhcGFjZWAuCgojIFNhbXBsZSBFeGFtcGxlCgojIyBMb2FkIGxpYnJhcmllcwoKYGBge3Isd2FybmluZz1GQUxTRSxtZXNzYWdlPUZBTFNFfQpsaWJyYXJ5KGZkYXBhY2UpCmxpYnJhcnkoZHBseXIpCmxpYnJhcnkoZ2dwbG90MikKbGlicmFyeShncmlkRXh0cmEpCmxpYnJhcnkoc2NhbGVzKQpgYGAKCiMjIExvYWQgZXhhbXBsZSBkYXRhCgpgYGB7cn0KZGF0YSgibWVkZmx5MjUiKQpgYGAKCiMjIE1ha2UgRnVuY3Rpb25hbCBwcmljaXBhbCBjb21wb25lbnQgYW5hbHlzaXMgaW5wdXQKKiBJRHMgOiBpZGVudGlmaWNhdGlvbgoqIHRWZWMgOiB0aW1lIHZlY3RvcgoqIHlWZWMgOiB5IHZlY3RvcgoKYGBge3J9CkZsaWVzIDwtIE1ha2VGUENBSW5wdXRzKG1lZGZseTI1JElELG1lZGZseTI1JERheXMsbWVkZmx5MjUkbkVnZ3MpCmBgYAoKIyMgQ2x1c3RlcmluZwoKKiBTZWUgYWxzbywgKEZDbHVzdCkKKiBjbWV0aG9kIDogJ0VNQ2x1c3RlcicgKGRlZmF1bHQpLCAna0NGQycKKiBkZWZhdWx0IG9wdGlvbnM6CiAgKyBtZXRob2RNdUNvdkVzdCA9ICJzbW9vdGgiIDogbWV0aG9kIHRvIGVzdGltYXRlIFtjcm9zcy1zZWN0aW9uYWwoZGVmYXVsdCksIHNtb290aF0KICArIEZWRXRocmVzaG9sZCA9IDAuOTAgOiBmcmFjdGlvbi1vZi12YXJpYW5jZS1leHBsYWluZWQgYnkgdGhlIGNvbXBvbmVudHMgKDAtMSkKICArIG1ldGhvZEJ3Q292ID0gJ0dDVicgOiBiYW5kd2lkdGggY2hvaWNlIG1ldGhvZCBmb3IgdGhlIHNtb290aGVkIGNvdmFyaWFuY2UgZnVuY3Rpb24KICArIG1ldGhvZEJ3TXUgPSAnR0NWJyA6IGJhbmR3aWR0aCBjaG9pY2UgbWV0aG9kIGZvciB0aGUgbWVhbiBmdW5jdGlvbgoKPiBDaGVuIGFuZCBNYWl0cmEgKDIwMTUpCj4gQ2hpb3UgYW5kIExpICgyMDA3KQoKYGBge3J9Cm5ld0NsdXN0IDwtIEZDbHVzdCgKICBGbGllcyRMeSxGbGllcyRMdCxrPTIsCiAgb3B0bnNGUENBID0gbGlzdCgKICAgIG1ldGhvZE11Q292RXN0PSJzbW9vdGgiLAogICAgdXNlckJ3Q292PTIsCiAgICBGVkV0aHJlc2hvbGQ9MC45MAogICkKKQpgYGAKCiMjIE9ic2VydmF0aW9uCgpBZnRlciBvYnNlcnZpbmcgZGF0YSBjbG9zZWx5LCB3ZSBmb3VuZCB0aGF0IGNsdXN0ZXJzIGFyZSBkaWZmZXJlbnRpYXRlZCBieSB0aGUgbnVtYmVyIG9mIGVnZ3MgdGhhdCBjb3VsZCBiZSBsYWlkLiBUaGUgdGhyZXNob2xkIHZhbHVlIG1heSBiZSAyNS4KCmBgYHtyfQp2ZXJ5TG93Q291bnQgPSBpZmVsc2UoCiAgc2FwcGx5KHVuaXF1ZShtZWRmbHkyNSRJRCksIGZ1bmN0aW9uKHUpIAogICAgc3VtKG1lZGZseTI1JG5FZ2dzW21lZGZseTI1JElEPT11XSkpPj0yNSwxLDIpCnZlcnlMb3dDb3VudApgYGAKClRodXMsIHRoZSBhY2N1cmFjeSBpcyBjYWxjdWxhdGVkIGJ5OgoKCmBgYHtyfQpzdW0oKHZlcnlMb3dDb3VudD09bmV3Q2x1c3QkY2x1c3RlcikpL2xlbmd0aCh1bmlxdWUobWVkZmx5MjUkSUQpKQpgYGAKCmBgYHtyfQpjMWZsaWVzIDwtIG1lZGZseTI1W25ld0NsdXN0JGNsdXN0ZXI9PTEsXQpjMmZsaWVzIDwtIG1lZGZseTI1W25ld0NsdXN0JGNsdXN0ZXI9PTIsXQpgYGAKCgpgYGB7cn0KYzFmbGllc09iaiA8LSBNYWtlRlBDQUlucHV0cyhjMWZsaWVzJElELGMxZmxpZXMkRGF5cyxjMWZsaWVzJG5FZ2dzKQpjMmZsaWVzT2JqIDwtIE1ha2VGUENBSW5wdXRzKGMyZmxpZXMkSUQsYzJmbGllcyREYXlzLGMyZmxpZXMkbkVnZ3MpCmBgYAoKYGBge3J9CmMxZmxpZXNGcGNhIDwtIEZQQ0EoYzFmbGllc09iaiRMeSxjMWZsaWVzT2JqJEx0LGxpc3QobWV0aG9kTXVDb3ZFc3Q9InNtb290aCIpKQpwbG90KGMxZmxpZXNGcGNhKQpgYGAKCmBgYHtyfQpjMmZsaWVzRnBjYSA8LSBGUENBKGMyZmxpZXNPYmokTHksYzJmbGllc09iaiRMdCxsaXN0KG1ldGhvZE11Q292RXN0PSJzbW9vdGgiKSkKcGxvdChjMmZsaWVzRnBjYSkKYGBgCgoKYGBge3J9CnBhcihtZnJvdz1jKDEsMikpCkNyZWF0ZU1vZGVPZlZhclBsb3QoYzFmbGllc0ZwY2EsbWFpbj0iQ2x1c3RlciAxIikKQ3JlYXRlTW9kZU9mVmFyUGxvdChjMmZsaWVzRnBjYSxtYWluPSJDbHVzdGVyIDIiKQpwYXIobWZyb3c9YygxLDEpKQpgYGAKCg==