# Generating quantities from Gaussian processes

Hello, the Gaussian Processes chapter in the manual has this example:

data {
int<lower=1> N;
array[N] real x;
vector[N] y;
}
transformed data {
vector[N] mu = rep_vector(0, N);
}
parameters {
real<lower=0> rho;
real<lower=0> alpha;
real<lower=0> sigma;
}
model {
matrix[N, N] L_K;
matrix[N, N] K = cov_exp_quad(x, alpha, rho);
real sq_sigma = square(sigma);

// diagonal elements
for (n in 1:N) {
K[n, n] = K[n, n] + sq_sigma;
}

L_K = cholesky_decompose(K);

rho ~ inv_gamma(5, 5);
alpha ~ std_normal();
sigma ~ std_normal();

y ~ multi_normal_cholesky(mu, L_K);
}

But it does not show how to simulate guantities for y under this setup. It does show later how to do that when there is x2, using the gp_pred_rng function:

functions {
vector gp_pred_rng(array[] real x2,
vector y1,
array[] real x1,
real alpha,
real rho,
real sigma,
real delta) {
int N1 = rows(y1);
int N2 = size(x2);
vector[N2] f2;
{
matrix[N1, N1] L_K;
vector[N1] K_div_y1;
matrix[N1, N2] k_x1_x2;
matrix[N1, N2] v_pred;
vector[N2] f2_mu;
matrix[N2, N2] cov_f2;
matrix[N2, N2] diag_delta;
matrix[N1, N1] K;
for (n in 1:N1) {
K[n, n] = K[n, n] + square(sigma);
}
L_K = cholesky_decompose(K);
K_div_y1 = mdivide_left_tri_low(L_K, y1);
K_div_y1 = mdivide_right_tri_low(K_div_y1', L_K)';
k_x1_x2 = cov_exp_quad(x1, x2, alpha, rho);
f2_mu = (k_x1_x2' * K_div_y1);
v_pred = mdivide_left_tri_low(L_K, k_x1_x2);
cov_f2 = cov_exp_quad(x2, alpha, rho) - v_pred' * v_pred;
diag_delta = diag_matrix(rep_vector(delta, N2));

f2 = multi_normal_rng(f2_mu, cov_f2 + diag_delta);
}
return f2;
}
}
data {
int<lower=1> N1;
array[N1] real x1;
vector[N1] y1;
int<lower=1> N2;
array[N2] real x2;
}
transformed data {
vector[N1] mu = rep_vector(0, N1);
real delta = 1e-9;
}
parameters {
real<lower=0> rho;
real<lower=0> alpha;
real<lower=0> sigma;
}
model {
matrix[N1, N1] L_K;
{
matrix[N1, N1] K = cov_exp_quad(x1, alpha, rho);
real sq_sigma = square(sigma);

// diagonal elements
for (n1 in 1:N1) {
K[n1, n1] = K[n1, n1] + sq_sigma;
}

L_K = cholesky_decompose(K);
}

rho ~ inv_gamma(5, 5);
alpha ~ std_normal();
sigma ~ std_normal();

y1 ~ multi_normal_cholesky(mu, L_K);
}
generated quantities {
vector[N2] f2;
vector[N2] y2;

f2 = gp_pred_rng(x2, y1, x1, alpha, rho, sigma, delta);
for (n2 in 1:N2) {
y2[n2] = normal_rng(f2[n2], sigma);
}
}

Can someone fill in the gap? I feel that it is straight-forward but I am still learning, and I need to follow along first. Much Appreciated~

What specifically are you trying to do here? The Stan program you quote from the User’s Guide has declares y as data, which means you have to supply it to the Stan program. There’s no way to have a variable supplied as data and simulated in Stan.

The prediction rng is assuming you have the data variables and just need to generate the y. There’s no way to generate the y from scratch in a GP as the values are conditional on the data.

If you want to just do a straight-up simulation from a GP for which you know the parameters, you have to write a different Stan program. Usually that can be done using only the generated quantities block.

Sorry. I misunderstood and now I am clear. Thank you.