Ich habe ein Experiment in der Coder-Sektion von PsychoPy entwickelt. Es ist eine relativ einfache Aufgabe, erfordert aber viel Text und Bild. Ich habe versucht, das ganze Experiment läuft (besteht aus 123 Studien) vor ein paar Tagen, und um den 28. Iteration erhielt ich folgende Fehlermeldung:PsychoPy textStim Speicherleck Problem
WindowsError: Ausnahme: Zugriffsverletzung schriftlich 0x00000004
ich in diese sah, und Es scheint, dass in Pyglet ein Speicherleck auftritt, der beim Zeichnen einer großen Menge von Textstimulationen im Fenster auftritt. Ich habe meinen Code so verfeinert, dass nur die Textkomponenten geändert werden, wenn das Experiment es erfordert. Ich liste meinen gesamten Code unten als Referenz:
from __future__ import division
from psychopy import locale_setup, visual, core, event, data, gui
import numpy as np
import pandas as pd
import sys, os, csv, time, random
from win32api import GetSystemMetrics
#Directory:
cwd = os.path.dirname(os.path.abspath(__file__))
#GUI:
expName = "CMNT"
expInfo = {"participant": "", "session": "001", "condition": "F1"} #Condition Files: F1, F2, M1, or M2
condition = expInfo["condition"]
condition = expInfo["condition"]
dlg = gui.DlgFromDict(dictionary = expInfo, title = expName, order = ["participant","session","condition"])
if dlg.OK == False:
core.quit()
#Window:
win = visual.Window(size = (GetSystemMetrics(0), GetSystemMetrics(1)), fullscr = True, pos = (0,0), units = "norm", color = "Gray")
#Turn off Mouse
event.Mouse(visible = False)
#Timers:
timer = core.Clock()
breakTimer = core.Clock()
#Load Condition File:
stim_df = pd.read_csv("exp_stimuli.csv", nrows = 124)
run_length = 123
#Output Directory:
fileLocation = cwd + "\%s_data\%s" %(expName, expInfo["participant"])
if not os.path.exists(fileLocation):
os.makedirs(fileLocation)
os.chdir(fileLocation)
if os.path.isfile("logFile.csv"):
os.remove("logFile.csv")
#List and Panda File Header
run_param_list = []
header = ["Block","MentalState", "Condition", "Speaker","Prompt", "RespButton", "CorrAnswer","RT(sec)", "ACC"]
#Define text and image stimuli
text = visual.TextStim(win = win, text = '', height = 0.1, pos = (0,0), color="White")
image = visual.ImageStim(win = win, pos = (0,0), size = (0.1,0.1), image = cwd + "\\" + "gray.png")
#Run Instruction Page:
text.text = '\t\tREMEMBER:\n\t\tAnswer each question,\n\t\t"Which should I pick?"\n\t\tusing the LEFT and RIGHT\n\t\tarrow key.'
text.height = 0.1
text.draw()
win.flip()
while True:
theseKeys = event.getKeys()
if "escape" in theseKeys:
core.quit()
if len(theseKeys):
break
#Begin Trials:
for i in xrange(run_length):
if stim_df["MentalState"][i] == "0":
breakTimer.reset()
while breakTimer.getTime() < 15.0:
text.text = "+"
text.height = 0.25
text.pos = (0,0)
text.draw()
win.flip()
else:
#win.flip()
timer.reset()
exit_press = []
event_press = []
speaker = visual.TextStim(win, text = stim_df["speaker"][i], height = 0.1, pos = (0,0.6))
speaker.setAutoDraw(True)
#0.5 seconds
while timer.getTime() < 0.5:
win.flip()
#3.0 seconds
if stim_df["speaker"][i] == "Computer":
text.text = stim_df["prompt"][i]
text.pos = (-0.1,0)
text.height = 0.08
text_box_length = text.boundingBox[0]/GetSystemMetrics(0)*2
image.image = cwd + "\\" + "gray.png"
image.pos = (-0.1,0)
image.size = (text_box_length, 0.35)
image.draw()
text.draw()
else:
text.text = stim_df["prompt"][i]
text.pos = (-0.1,0)
text.height = 0.08
text_box_length = text.boundingBox[0]/GetSystemMetrics(0)*2
image.image = cwd + "\\" + "blue.png"
image.pos = (-0.1,0)
image.size = (text_box_length, 0.35)
image.draw()
text.draw()
win.flip()
while timer.getTime() < 3.5:
exit_press += event.getKeys()
if "escape" in exit_press:
core.quit()
onset_Time = timer.getTime()
speaker.setAutoDraw(False)
#3.5 seconds
text.text = stim_df["question"][i]
text.pos = (0,0.6)
text.height = 0.1
text.draw()
text.text = stim_df["answerA"][i]
text.pos = (-0.3, -0.5)
text.draw()
text.text = stim_df["answerB"][i]
text.pos = (0.3, -0.5)
text.height = 0.1
text.draw()
win.flip()
length = 0
while timer.getTime() < 7.0:
event_press += event.getKeys(keyList = ["left","right"])
if len(event_press) > length:
RT = timer.getTime() - onset_Time
length = len(event_press)
elif len(event_press) == 0:
RT = "N/A"
exit_press += event.getKeys()
if "escape" in exit_press:
core.quit()
#Jitter 1 time
text.text = "+"
text.pos = (0,0)
text.height = 0.25
text.draw()
win.flip()
while timer.getTime() < 7.0 + (stim_df["jitter1"][i]/1000):
exit_press += event.getKeys()
if "escape" in exit_press:
core.quit()
#Check Conditional Input
try:
response = event_press[-1]
except:
response = None
if response == "left":
reply = stim_df["answerA"][i]
if reply == stim_df["corrAnswer"][i]:
acc = 1
else:
acc = 0
elif response == "right":
reply = stim_df["answerB"][i]
if reply == stim_df["corrAnswer"][i]:
acc = 1
else:
acc = 0
elif response == None:
response = "N/A"
reply = stim_df["corrAnswer"][i]
acc = 0
text.text = reply
text.height = 0.08
text.pos = (0.1,0.3)
#2 seconds
if stim_df["speaker"][i] == "Computer":
text.text = reply
text.height = 0.08
text.pos = (0.1,0.3)
speaker.draw()
image.image = cwd + "\\" + "gray.png"
image.size = (text.boundingBox[0]/GetSystemMetrics(0)*2 + 0.2, text.boundingBox[1]/GetSystemMetrics(1)*2 + 0.1)
image.pos = (0.1, 0.3)
image.draw()
text.draw()
text.pos = (-0.1,-0.1)
text.text = reply + u" \u2713"
text_box_length = text.boundingBox[0]/GetSystemMetrics(0)*2 + 0.1
image.image = cwd + "\\" + "gray.png"
image.size = (text.boundingBox[0]/GetSystemMetrics(0)*2 + 0.1, text.boundingBox[1]/GetSystemMetrics(1)*2 + 0.1)
image.pos = (-0.1,-0.1)
image.draw()
text.draw()
else:
text.text = reply
text.height = 0.08
text.pos = (0.1,0.3)
speaker.draw()
image.image = cwd + "\\" + "green.png"
image.size = (text.boundingBox[0]/GetSystemMetrics(0)*2 + 0.1, text.boundingBox[1]/GetSystemMetrics(1)*2 + 0.1)
image.pos = (0.1,0.3)
image.draw()
text.draw()
text.text = reply + " :)"
text.pos = (-0.1,-0.1)
image.image = cwd + "\\" + "blue.png"
image.size = (text.boundingBox[0]/GetSystemMetrics(0)*2 + 0.1, text.boundingBox[1]/GetSystemMetrics(1)*2 + 0.1)
image.pos = (-0.1, -0.1)
image.draw()
text.draw()
win.flip()
while timer.getTime() < 9.0 + (stim_df["jitter1"][i]/1000):
exit_press += event.getKeys()
if "escape" in exit_press:
core.quit()
#Jitter 2 time
text.text = "+"
text.height = 0.25
text.pos = (0,0)
text.draw()
win.flip()
while timer.getTime() < 11.0 + (stim_df["jitter1"][i]/1000) + (stim_df["jitter2"][i]/1000):
exit_press += event.getKeys()
if "escape" in exit_press:
core.quit()
#Panda Output File
run_param_list.append([stim_df["block"][i], stim_df["MentalState"][i], condition, stim_df["speaker"][i], stim_df["prompt"][i], response, stim_df["corrAnswer"][i], RT, acc])
fid = pd.DataFrame(run_param_list, columns = header)
fid.to_csv("logFile.csv", header = True)
#Close up Shop:
win.close()
core.quit()
ich mich gefragt, ob jemand einen Vorschlag zu hat, wie der Code zu verfeinern besser, so dass der Speicherverlust Fehler werden nicht auftreten. Wenn dieser Fehler nicht behoben werden kann, wäre es die beste Lösung, das Experiment mit PsychoPy Builder zu replizieren?
Die Entwicklung eines minimalen reproduzierbaren Beispiels würde Ihnen helfen, das Problem einzugrenzen und die Wahrscheinlichkeit zu erhöhen, dass jemand Ihren Code tatsächlich liest. –
, d. H. Es ist schwer zu sagen, ob Sie tatsächlich der festgelegten Anleitung folgen, um nur die Texteigenschaft eines Textreizes zu aktualisieren, wenn sich dieser Wert tatsächlich geändert hat. Auch, wo immer es möglich ist, erstellen Sie keine Textreize mehrmals. Erstellen Sie sie einmal und aktualisieren Sie dann ihre Eigenschaften nach Bedarf. –
Hallo Michael, könntest du erklären, was die etablierte Anleitung ist, um Text- und Bildreize richtig zu aktualisieren, weil ich dachte, ich würde es richtig machen. Zum Beispiel setze ich am oberen Rand meines Skripts eine Bildvariable mit dem Namen image und dann im Rest des Scripts, wenn ich eines seiner Attribute ändern muss (zB Position, das Bild selbst), dann würde ich es ändern, indem ich image mache .image = etc, image.pos = usw. Ich dachte, dass diese Methode eine gute Möglichkeit ist, Speicher zu sparen. Gibt es eine effizientere Möglichkeit, ihre Eigenschaften zu aktualisieren? – djl