Dear stan community,
I have a question that is rather a “nice thing to have” than an error/ necessity.
If I see correctly, in stan, to extract values from vectors or matrices, I need to provide indices of the rows/columns from which to extract those values.
These indices need to be integers (obviously given that non-integer rows/ columns are note defined).
However, afaics, the only objects that stan allows to be integers are those defined under data
or transformed data
.
Sometimes, it can however be nice to create a temporary object that is an scalar integer (e.g. the stimulus ID or the response on a particular trial in a cognitive task) and that is then used repeatedly as an index to extract certain bits of data from other vectors/ matrices. Just for convenience (to avoid multiple nesting of several objects with brackets into each other).
Question:
Afaics stan does not allow objects in the parameters
or transformed parameters
to be integers… is there another way to define such temporary objects?
Here a short example:
data {
int<lower=0> nStim; // number of stimuli
int<lower=0> nResp; // number of responses
int<lower=0> nTrial; // number of trials per subject
int<lower=0> nSub; // number of subject
int<lower=1> stimuli[nSub,nTrial]; // stimulus identifier 1-12
int<lower=0, upper=1> resp[nSub,nTrial]; // responses (1/0)
int<lower=-1, upper=1> outcome[nSub,nTrial]; // outcomes (-1 or 1)
matrix[nStim,nResp] Qi; // initial action values: for each stimulus (rows), response (columns), used to initialize Q
}
// ... dropping some code here...
transformed parameters {
matrix[nStim,nResp] Q; // Current action values for all cues: for each cue, for each response (12x2)
// Learning model:
for (iSub in 1:nSub){ // Loop over subjects
// Initialize variables:
Q = Qi; // Initialize action values for all cues
for(iTrial in 1:nTrial){ // Loop over trials
// Retrieve settings for this trial
for(iResp in 1:nResp){ // For each possible response:
q[iResp] = Q[nStim,iResp]; // Retrieve action value given cue s seen in this trial iTrial of this subject iSub
}
// Update Q-values:
PE = outcome[iSub,iTrial] - Q[stimuli[iSub,iTrial],2-resp[iSub,iTrial]]; // Compute prediction error
Q[stimuli[iSub,iTrial],2-resp[iSub,iTrial]] = Q[stimuli[iSub,iTrial],2-resp[iSub,iTrial]] + epsilon[iSub]*PE; // Update Q-values
}
}
You see that in the last row,
- I need indices for the
stimuli
and theresp
matrices, and the outputs of these matrices are again indices for theQ
matrix… and there can be cases with even more nesting. - I have to hard-code the transformation of the 0/1 values in the
resp
matrix into 1/2 in order to use them as indices forQ
—every time I use theresp[iSub,iTrial]
in my code.
Could I somehow define temorary objects s
and r
like
s = stimuli[iSub,iTrial];
r = 2 - resp[iSub,iTrial]];
that are integers and can be used for further indexing?
Thanks already for any pointers!