Repeated measures ANOVA in R
August 24, 2008 at 04:46 PMRepeated measures ANOVAs in R are performed with the aov() function. The aov() function requires fully balanced data to work correctly, i.e., there can be no missing values in the data. In order to use aov() on data with missing values (most experimental data has excluded values), one needs to average over subjects or items.
Below, we assume a data frame data with at least the columns subject, factor1, factor2, and logRT. The code below averages over subjects, returning the data frame data.subject.
data.subject = aggregate(data$logRT, list(data$subject, data$factor1, data$factor2), mean)
colnames(data.subject) = c("subject", "factor1", "factor2", "logRT")
An alternative is to use the excellent reshape package.
library(reshape) data.subject = recast(data, SUBJ + factor1 + factor2 ~ variable, mean, measure.var="logRT")
You can then perform the repeated measures ANOVA on data.subject.
summary(aov(logRT ~ factor1 * factor2 + Error(subject/(factor1 * factor2)), data=data.subject))
Linger-process: Really easy Linger data pre-processing in Ruby
August 23, 2008 at 11:05 PMThis is a set of Ruby classes for processing data output from Doug Rohde's Linger software for self-paced reading experiments.
Simply stated, it takes raw Linger output and turns it into a table for use in R.
The latest working version is available from github. A usage example is below.
require "linger-process.rb"
# A new Experiment object takes four arguments, two of which are required:
# (1) required, Array that specifies the names of the experiment(s)
# (2) required, Hash that specifies how the conditions should be expanded
# (3) optional, String that specifies the directory containing the Linger data,
# defaults to "./data/"
# (4) optional, Array of symbols that specifies what columns should be output,
# defaults to
# [:words, :word_lengths, :word_positions, :regions, :experiment, :subject,
# :item, :condition, :sentence_number, :list_position, :reading_times,
# :log_reading_times, :accuracy]
experiment_names = ["principB", "principC"]
# Here, for example, the condition coded as TNN in the raw data is
# expanded out to the factors RC, N, and U. You can specify as many
# conditions and factors as necessary.
factors = { "TNN" => %w(RC N U),
"TNM" => %w(RC M U),
"QNN" => %w(HN N U),
"QMN" => %w(HN M G)}
data_directory = "./example-input-data/"
columns = [:experiment, :subject, :item, :condition, :factors, :regions,
:reading_times, :log_reading_times, :words, :word_lengths,
:word_positions, :list_position, :accuracy]
experiment = Experiment.new(experiment_names, factors, data_directory, columns)
# All processing is done within the object. There are two
# options for outputting the processed data. You can either output
# it to STD_OUT (to check that everything went smoothly), or you can
# save it to a file.
#puts experiment # to STDOUT
experiment.to_file("example-output-data.txt") # to a file
Calculating d-prime in R
August 23, 2008 at 11:04 PMThis function takes a data frame data.frame and returns a d-prime score for each unique entry in the subject column of the data frame. Note that the function will return Inf or -Inf if any value in Hrate or Frate is 1 or 0.
dprime = function(data.frame) {
yes = subset(data.frame, resp=="Y")
no = subset(data.frame, resp=="N")
hit = subset(data.frame, resp=="Y" & acc == 1)
falsealarm = subset(data.frame, resp=="N" & acc == 0)
Hrate = xtabs(~subject,data=hit)/xtabs(~subject,data=yes)
Frate = xtabs(~subject,data=falsealarm)/xtabs(~subject,data=no)
dprime_score = qnorm(Hrate) - qnorm(Frate)
return(dprime_score)
}