Spoonerism task

Summary of analysis criteria

Criteria to calculate point-time values

  • Input end: The end of the researcher’s utterance.
  • Answer start: First syllable, excluding “ehm” or similar fillers. Even if the syllables stops, e.g., “du…” when target is “duna”.
  • Answer end: The end of the participant’s answer, including any corrections or changes they make.

Criteria to calculate rt for each trial

  • Formula: answer_end - input_end

Criteria for accuracy

  • 2 points: correct answer
  • 1 point: correct phoneme switch, wrong word
  • 0 point: incorrect
  • NA VALUES: participants’ forgot the prompt or did not answer

Calculating RT

# reaction time 

df %>% 
  # mutate raw time: seconds to milliseconds 
  
  mutate(input_end = input_end*1000, 
         answer_start = answer_start*1000, 
         answer_end = answer_end*1000) %>% 
  
  # create rt variables NOTE: CHECK THIS! 
  
  mutate(rt_trial = answer_end - input_end) %>% 
  
  # remove columns 
  
  dplyr::select(-input_end, -answer_start, -answer_end) -> df

Calculating accuracy

# load accuracy data 
read_csv("ACC_spoonerism.csv") %>% 
  
# check this: exclude for different phonemes at the beginning 
  filter(item != "C" & item != "I") %>% 

# calculate accuracy
  
  mutate(accuracy = case_when(
    # if response is correct == 2
    response == target ~ 2,
    
    # if phoneme-switching only is correct == 1
    substr(response, 1, 1) == substr(target, 1, 1) ~ 1,
    
    #else == 0
    TRUE ~ 0
  )) %>% 
  
  # create accuracy as factor (1 only for correct answers)
  
  mutate(accuracy_fct = if_else(
    accuracy == 2, 1, 0
  )) %>% 
  
  # create a total accuracy score for each participant
  
  group_by(ID) %>% 
  mutate(tot_accuracy = sum(accuracy)) %>% 
  ungroup()-> acc

### check 
# length(unique(acc$ID)) #94

Speed-accuracy trade off

## Create speed-accuracy trade-off measure 

### BIS combines reaction times and error rates in a way that strongly attenuates speed-accuracy trade-offs (see the paper for details). If you use one of these functions, please cite: Liesefeld, H. R. & Janczyk, M. (2019). Combining speed and accuracy to control for speed-accuracy trade-offs(?). Behavior Research Methods, 51, 40-60. doi:10.3758/s13428-018-1076-x

BIS <- function(data) {
  n <- length(data$group)    # sample size to correct var()-function result (which uses n-1)
  srt <- sqrt( ((n-1)/n) * var(data$mean_rt_c) )     # sample standard deviation across all rts
  spc <- sqrt( ((n-1)/n) * var(data$pc) )            # sample standard deviation across all rts
  mrt <- mean(data$mean_rt_c)                        # mean across all rts
  mpc <- mean(data$pc)                               # mean across all pcs
  zrt <- (data$mean_rt_c-mrt)/srt                    # standardized rts
  zpc <- (data$pc-mpc)/spc                           # z-standardized pcs
  data$bis <- zpc - zrt                              # Balanced Integration Score
  
  return(data)                                       # return data.frame with added variable 'bis'
}

### BIS with pa.rt (less strict accuracy score)

df1 %>% 
  select(ID, pa.acc, pa.rt) %>% 
  mutate(pa.acc = pa.acc/40) %>% 
  rename(
    group = ID,
    pc = pa.acc,
    mean_rt_c = pa.rt
  ) %>% BIS() %>% 
  select(group, bis) %>% 
  rename(ID = group) -> df.bis
left_join(df1, df.bis, by = "ID") %>% 
  rename(tot.bis.pa = bis)-> df1

### BIS with pa.rt2 (more strict accuracy score)

df1 %>% 
  select(ID, pa.acc, pa.rt2) %>% 
  mutate(pa.acc = pa.acc/40) %>% 
  rename(
    group = ID,
    pc = pa.acc,
    mean_rt_c = pa.rt2
  ) %>% BIS() %>% 
  select(group, bis) %>% 
  rename(ID = group) -> df.bis
left_join(df1, df.bis, by = "ID") %>% 
  rename(tot.bis.pa2 = bis)-> df1

Exclude participants

df1 %>% 
  filter(group == "DYS" | (group == "TD" & is.na(other_diagnoses))) %>% 
  filter(!startsWith(ID, "VER")) -> df1

df1 %>%
  mutate(
    exclude = case_when(
      ID == "VER02" ~ 1, # ADHD - university - DYS
      ID == "VER04" ~ 1, # ADHD - university - DYS
      ID == "MEN12" ~ 1, # discalculia - 3rd - TD
      ID == "MEN18" ~ 1, # disgrafia, discalculia - 3rd - TD
      ID == "MEN26" ~ 1, # disgrafia - 5th - TD, 
      ID == "LAE33" ~ 1, # disgrafia, disortografia, 3rd - TD, 
      
      ### new exclusion criteria: 
      ID == "LAE38" ~ 1,
      ID == "LC19" ~ 1, 
      ID == "MEN29" ~ 1, 
      ID == "MEN02" ~ 1, 
      
      
      ID == "MEN10" ~ 1, 
      ID == "LAE23" ~ 1, 
      # ID == "MEN35" ~ 1, 
      TRUE ~ 0
    )
  ) %>%
  filter(exclude == 0) %>%
  
  # stricter crtiteria 
  # filter(group.exclusion != "PR") %>% 
  
  # less strict criteria 
  # filter(group == "DYS" | (group == "TD" & reading.score > -2)) %>%
  
  
  filter(ID != "VER01" & ID != "VER03") %>% 
  dplyr::select(-exclude) -> df1

Descriptive analysis of RT, accuracy and BIS

Descriptive measures
Group Accuracy (M) SD range RT (M) SD range Speed-Accuracy trade-off (M) SD range
DYS 30.41 7.28 10 9.29 0.50 8.27 -1.44 2.12 -6.47
DYS 30.41 7.28 40 9.29 0.50 10.10 -1.44 2.12 1.68
TD 36.98 3.09 26 8.54 0.45 7.45 0.99 0.91 -2.12
TD 36.98 3.09 40 8.54 0.45 9.36 0.99 0.91 2.13

Inferential Statistics

RT

# model rt ~ group 
df1 %>% 
  mutate_if(is.character, as.factor) %>% 
  mutate(pa.rt = log(pa.rt),
         age = scale(age), age = as.double(age)) %>% 
  
  # model formula
  lm(formula = 
       pa.rt ~ 
       # group * age
       group + 
       age 
     ) -> m1 

tab_model(m1)
  pa rt
Predictors Estimates CI p
(Intercept) 9.32 9.14 – 9.49 <0.001
group [TD] -0.79 -1.01 – -0.56 <0.001
age -0.05 -0.16 – 0.06 0.377
Observations 80
R2 / R2 adjusted 0.389 / 0.373
Spoonerism: RT
Group Estimate SE CI
DYS 9.32 0.09 9.14 - 9.49
TD 8.53 0.07 8.4 - 8.66
Spoonerism: RT
Sum Sq Df F value Pr(>F)
group 10.29 1 47.18 0.000
age 0.17 1 0.79 0.377
Residuals 16.79 77 NA NA
AIC AICc BIC R2 R2_adjusted RMSE Sigma
110.13 110.67 119.66 0.39 0.37 0.46 0.47

Accuracy

# Accuracy 
df1 %>% 
  # prepare data 
  mutate_if(is.character, as.factor) %>% 
  mutate(age = scale(age), age = as.double(age)) %>% 
  
  # model   
  glm(formula = 
       
       pa.acc ~ 
       group * age, 
       # group, 
       # age, 
      
      family = poisson(link = "log")
     
     ) -> m2

tab_model(m2)
  pa acc
Predictors Incidence Rate Ratios CI p
(Intercept) 28.79 26.61 – 31.07 <0.001
group [TD] 1.28 1.17 – 1.41 <0.001
age 1.13 1.04 – 1.22 0.004
group [TD] × age 0.88 0.80 – 0.97 0.008
Observations 80
R2 Nagelkerke 0.483
Spoonerism: Accuracy
Group Estimate SE CI
DYS 28.79 0.04 26.64 - 31.1
TD 36.94 0.02 35.27 - 38.7
Spoonerism: Accuracy
LR Chisq Df Pr(>Chisq)
group 30.67 1 0.000
age 8.48 1 0.004
group:age 6.99 1 0.008
AIC AICc BIC R2_Nagelkerke RMSE Sigma Score_log Score_spherical
497.32 497.85 506.84 0.48 4.61 1 -3.06 0.11
emtrends(m2, pairwise ~ group, var = "age", infer = T, adjust = "bonferroni")$emtrends %>% summary() %>% as.data.frame() %>% 
  mutate(across(age.trend:z.ratio, ~round(.x,2)), 
                                                                                                                               p.value = round(p.value, 3)) %>% 
  kable(caption = "Age * Group") %>% kable_styling()
Age * Group
group age.trend SE df asymp.LCL asymp.UCL z.ratio p.value
DYS 0.12 0.04 Inf 0.04 0.20 2.91 0.004
TD 0.00 0.02 Inf -0.05 0.04 -0.19 0.849

BIS

# BIS 
df1 %>% 
  # prepare data 
  mutate_if(is.character, as.factor) %>% 
  mutate(age = scale(age), age = as.double(age)) %>% 
  
  # model   
  lm(formula = 
       
       tot.bis.pa ~ 
       group * age 
       # group, 
       # age 
     
     ) -> m3

tab_model(m3)
  tot bis pa
Predictors Estimates CI p
(Intercept) -1.86 -2.44 – -1.28 <0.001
group [TD] 2.84 2.14 – 3.55 <0.001
age 1.02 0.38 – 1.65 0.002
group [TD] × age -1.04 -1.78 – -0.30 0.007
Observations 80
R2 / R2 adjusted 0.467 / 0.446
Spoonerism: RT
Group Estimate SE CI
DYS -1.86 0.29 -2.44 - -1.28
TD 0.98 0.20 0.58 - 1.38
Spoonerism: RT
Sum Sq Df F value Pr(>F)
(Intercept) 79.76 1 41.13 0.000
group 126.18 1 65.06 0.000
age 19.83 1 10.23 0.002
group:age 15.18 1 7.83 0.007
Residuals 147.39 76 NA NA
AIC AICc BIC R2 R2_adjusted RMSE Sigma
285.91 286.72 297.82 0.47 0.45 1.36 1.39
emtrends(m3, pairwise ~ group, var = "age", infer = T, adjust = "bonferroni")$emtrends %>% summary() %>% as.data.frame() %>% 
  
  mutate(across(age.trend:t.ratio, ~round(.x,2)), 
                                                                                                                               p.value = round(p.value, 3)) %>% 
  kable(caption = "Age * Group") %>% kable_styling()
Age * Group
group age.trend SE df lower.CL upper.CL t.ratio p.value
DYS 1.02 0.32 76 0.38 1.65 3.20 0.002
TD -0.02 0.19 76 -0.41 0.36 -0.13 0.899

Plot