Modeling

Summation space

Suppose that you have two sources of information that people can use to make an estimate of some physical attribute be it spatial or temporal. You might want to know whether the precision of the estimates used by subjects result from combining the two sources in specific ways. One nice way to check the extent of combination or integration is to use a summation space or pooling space. Here we will simulate different degrees of integration by applying a Quick’s pooling equation (Quick, 1974):

\[\frac{1}{\sigma_{f}} = \left[ \left(\frac{1}{\sigma_{e}}\right)^k + \left(\frac{1}{\sigma_{l}}\right )^k \right ]^{1/k}\]

Note that the precision can be defined as the reciprocal of the SD. We first load the packages and define the functions that we will need.

We define one function so as to draw a circle (prediction from mle k=2 in the pooling equation)

library(data.table) # we will need it later
library(ggplot2)

draw.pred <- function(k,n=500) # 
  {
    x <- seq(0,1,len=n)
    y <- (1-x^k)^(1/k)
    return(data.frame(x = x, y = y))
  }

The function to simulate the combined response, k is the parameter that determines the degree of combination

simul_comb <- function(cue1,cue2,k)
{
  sd1 <- sd(cue1)
  sd2 <- sd(cue2)
  precision.comb =  ( (1/sd1)^k + (1/sd2)^k )^(1/k) #Quick's pooling equation
  rnorm(length(cue1),0.3,1/precision.comb)
}

Finally, a function to simulate responses to individual cues

simul_resp <- function(n,cue=1)
{
  if(cue==1){ # parameters for cue 1
    mu <- 0.3
    sd <- runif(1,0.072,0.13) # less reliable than cue 2    
  }
  else{ # parameters for cue 2
    mu <- 0.3
    sd <- runif(1,0.022,0.064) # more reliable than cue 1
  }  
  rnorm(n,mu,sd)
}

We are ready know to simulate the responses. We will simulate 500 responses for 8 hypothetical subjects. We create a data table with one column (subj), with as many rows as number of respones times number of subjects:

  data1 <- data.table(subj=rep(seq(1,8),each=500))

We use mutate from dplyr to add columns consisting of 500 simulate responses for each subject.

#|message: false
#|cache: true

data1[,`:=`(resp_cue1=simul_resp(500,1),resp_cue2=simul_resp(500,2)),by=subj]

We add different kinds of combination (ls=linear summation, mle=maximum likelihood, ps=probability summation):

#|cache: true

data1[,`:=`(resp_ls=simul_comb(resp_cue1,resp_cue2,k=1),resp_mle=simul_comb(resp_cue1,resp_cue2,k=2),resp_ps=simul_comb(resp_cue1,resp_cue2,k=3.5)),by=subj]

We obtain SD summaries for each subject, cue and type of combined response

data.summary <- data1[,.(cue1.sd=sd(resp_cue1),cue2.sd=sd(resp_cue2),ls.sd=sd(resp_ls),mle.sd=sd(resp_mle),ps.sd=sd(resp_ps)),by=subj]

We compute the ratios of the different SD: For example, to check if responses in the linear summation condition do really follow linear summation (\(k=1\)), we compute two ratios: \(ratio1 = ls.sd/cue1.sd\) and \(ratio2= ls.sd/cue2.sd\). We will do the same for the other two types of combination.

#|label: adding ratios of SD

data.summary[,`:=`(ratio1.ls=ls.sd/cue1.sd,ratio2.ls = ls.sd/cue2.sd,ratio1.mle=mle.sd/cue1.sd,ratio2.mle=mle.sd/cue2.sd,ratio1.ps=ps.sd/cue1.sd,ratio2.ps=ps.sd/cue2.sd)]

Finally, we plot the different subjects and the different types of combinations in the summation space. In red we plot the combination generated by linear summation, MLE in blue and probability summation in green.

keq2 <- draw.pred(2,500) # predictions for mle (k=2)

keq35 <- draw.pred(3.5,500) # predictions for prob. summation (k = 3.5)

df <- data.table(x=c(0,1),xend=c(1,1),y=c(1,1),yend=c(1,0))

ggplot(data.summary) + 
  geom_point(aes(ratio1.ls,ratio2.ls),colour="red",size=4) +
  geom_point(aes(ratio1.mle,ratio2.mle),colour="blue",size=4) +  geom_point(aes(ratio1.ps,ratio2.ps),colour="green",size=4) +
  geom_segment(aes(x=x,xend=xend,y=y,yend=yend),linetype=3,colour="grey30",data=df)+
  geom_abline(intercept=1,slope=-1,colour="grey30") +
  geom_path(data=keq2,aes(x=x,y=y),linetype=2,colour="grey30") + geom_path(data=keq35,aes(x=x,y=y),linetype=3,colour="grey30") +
  scale_x_continuous("combined_cue/cue 1",breaks =seq(0,1,len=6)) +
  scale_y_continuous("combined_cue/cue 2",breaks =seq(0,1,len=6)) +
  theme_classic(18)

The solid line denotes the linear summation prediction, the dashed line corresponds to the mle prediction and the dotted curved line denotes probability summation (k between 3 and 4) and the straight dotted lines represent no combination at all (\(k=\infty\)).

We have used this approach (de la Malla et al. 2015) to analyse the degree of combination of different cues across time. One, however, have to be careful when interpreting the exponents of the models as pointed out in Pannunzi et al (2015)

References:

  1. Quick, R. F. (1974) Kybernetic 16, 65–67.
  2. de la Malla, C. and López-Moliner, J. (2015). Predictive plus online visual information optimizes temporal precision in interception. J Exp Psychol Hum Percept Perform, 41(5):1271–1280.
  3. Pannunzi, M., Pérez-Bellido, A., Pereda-Baños, A., López-Moliner, J., Deco, G., and Soto-Faraco, S. (2015). Deconstructing multisensory enhancement in detection. J Neurophysiol, 113(6):1800–18.

Quickpsy

quickpsy is just a new R package. With quickpsy you can fit psychometric functions to different conditions with very little code in R. It is designed to be user-friendly but also provides you with great flexibility (e.g. support for user-defined functions), speed and nice graphical output based on ggplot2.

Below you have a simple example:

library(quickpsy) # we will need it later
library(MPDiR) # contains the Vernier data; use ?Vernier for the reference
fit <- quickpsy(Vernier, Phaseshift, NumUpward, N,
                grouping = .(Direction, WaveForm, TempFreq))
plot(fit) + theme_classic()+ scale_color_brewer(type="qual",palette="Set1")

But you can do a lot, lot more in no time …

To get quickpsy and quickly learn how to use it, you can go to CRAN or visit this link at Dani’s web page and follow the directions for installation.

and … Enjoy it!!!

References: Linares, D. and López-Moliner, J. (2016). quickpsy: An R package to fit psychometric functions for multiple groups. The R Journal, 8(1):122–131.