Writing and saving logfiles

In cognitive science experiments, we will usually collect data from multiple participants in order to later analyse these. That is, it is critical that our experiment script write data to a file. Most often this will be a .csv file with detailed information about stimuli and responses. Python is not by default working with data frames, but we can import a module, called Pandas, that makes it easy to organise data in a data frame format ready for analysis in most stats softwares.

Lets import the Pandas module and some psychopy modules that comes handy later on including the "data" module:

# import modules
from psychopy import visual, data
import pandas as pd

Notice that if we import is pandas "as pd" we can use this short form later on rather than writing the full name "pandas".

In order to write trial-by-trail data into a data frame, we first need to define such a data frame. In principle it would be enough to write data = pd.DataFrame(). However, what can happen later on is that the order of columns in the resulting data frame can become rather disorganised, so we recommend defining the columns before starting to write data to these:

# define columns
columns = ['id', 'age', 'gender', 'condition', 'stimulus', 'response']  
# define dataframe
data = pd.DataFrame(columns = columns)

This creates an empty data frame. Usually this definition of the the data frame would be best placed in the early part of the script.

Later, when the experiment is complete we want to save the data frame with a unique name to make sure that we don't mistakenly overwrite it (PsychoPy will generally not warn us if are about to overwrite a logfile). We can generate a unique name by adding a participant id and a time stamp to the name. The participant id will often come from inputs to the dialogue box (see previous chapter). In the example below we assume that the participant id is the first argument in the ID variable from the dialogue box. It is a good idea to establish a dedicated directory for the logfiles. Lets imagine that we already made a directory called "logfiles".

# logfile directory
logfile_path = "logfiles/"

# participant id (ID is the variable written from the intro dialogue box)
id = ID[0]

# get date and time for unique logfile name
date = data.getDateStr()  

# logfile name
logfile_name = "{}logfile_{}_{}.csv".format(logfile_path, id, date)

The format() function will insert values into the curly brackets {}. Lets imagine that id = "001", and data is recorded Sep 11th 2018 at 12:00 o'clock, then the name will be "logfiles/logfile_001_2018_Sep_11_1200.csv"

Now we want to add trial-by-trial experiment data to the data frame. We do this by inserting the following code to our experiment loop:

# write a row to the logfile with data from an experiment trial 
data = data.append({
    'id': ID[0],
    'age': ID[1],
    'gender': ID[2],
    'condition': condition, 
    'stimulus': i,
    'response': response}, ignore_index=True)

Notice that the code needs to be indented relative to the for loop-command.

The last thing we need is to save the file when the experiment is complete. For this, we just need to add the following lines of code in the end of of our experiment script.

# save logfile
data.to_csv(logfile_name)

Now, in order to get a better overview over where to put these code snippets in a full experiment code lets provide an example, where in each trial an image is shown and the reaction time recorded.

# import  modules
from psychopy import visual, event, core, data                                
import glob
import pandas as pd

# dialogue box
dialogue = gui.Dlg(title = "The Experiment")
dialogue.addField("ID: ") 
dialogue.addField("age: ")
dialogue.addField("gender: ", choices=["Female", "Male", "Other" ])
dialogue.show()
if dialogue.OK: 
    ID = dialogue.data
elif dialogue.Cancel: 
    core.quit()

# define window
win = visual.Window(color = 'black') 

# path to the folder containing stimulus images
path = "images/"           

# fetch list of image file names
images = glob.glob(path + "*.jpg")

# initiate a clock 
stopwatch = core.Clock()

# define columns for logfile data frame 
columns = ['id', 'age', 'gender', 'condition', 'stimulus', 'response']  
# define dataframe
data = pd.DataFrame(columns = columns)

for i in images: 
    # prepare stimulus                                                         
    stimulus = visual.ImageStim(win, image = i, pos = [0,0])
    # draw stimulus  
    stimulus.draw()
    # flip window                                                               
    win.flip()

    # reset clock 
    stopwatch.reset()

    # wait for keypress                                                                   
    event.waitKeys()

    # get reaction time
    reaction_time = stopwatch.getTime() 



win.close

results matching ""

    No results matching ""