/* *
 * Title:        

* Description:

* Copyright: Copyright (c)

* Company:

* @author * @version 1.0 */ package umontreal.iro.lecuyer.stochprocess; import umontreal.iro.lecuyer.rng.*; import umontreal.iro.lecuyer.probdist.*; import umontreal.iro.lecuyer.randvar.*; /** * . * * This class represents an Ornstein-Uhlenbeck process * as in {@link OrnsteinUhlenbeckProcess}, but * the process is generated using the simple Euler scheme *

*

*
* X(tj) - X(tj-1) = α(b - X(tj-1))(tj - tj-1) + σ(t_j - t_j-1)1/2 Zj *

* where * Zj∼N(0, 1). * This is a good approximation only for small time intervals * tj - tj-1. * */ public class OrnsteinUhlenbeckProcessEuler extends OrnsteinUhlenbeckProcess { /** * Constructor with * parameters α = alpha, b, σ = sigma and initial * value * X(t0) = x0. The normal variates Zj will be * generated by inversion using the stream stream. * */ public OrnsteinUhlenbeckProcessEuler (double x0, double alpha, double b, double sigma, RandomStream stream) { this (x0, alpha, b, sigma, new NormalGen (stream)); } /** * Here, the normal variate generator is specified directly * instead of specifying the stream. * The normal generator gen can use another method than inversion. * */ public OrnsteinUhlenbeckProcessEuler (double x0, double alpha, double b, double sigma, NormalGen gen) { super (x0, alpha, b, sigma, gen); } /** * Generates and returns the next observation at time tj+1 = * nextTime. Assumes the previous observation time is tj defined * earlier (either by this method or by setObservationTimes), * as well as the value of the previous observation X(tj). * Warning: This method will reset the observations time tj+1 * for this process to nextTime. The user must make sure that * the tj+1 supplied is *  >= tj. * */ public double nextObservation() { double xOld = path[observationIndex]; double x = xOld + (beta - xOld) * alphadt[observationIndex] + sigmasqrdt[observationIndex] * gen.nextDouble(); observationIndex++; path[observationIndex] = x; return x; } public double nextObservation (double nextTime) { double previousTime = t[observationIndex]; double xOld = path[observationIndex]; observationIndex++; t[observationIndex] = nextTime; double dt = nextTime - previousTime; double x = xOld + alpha * (beta - xOld) * dt + sigma * Math.sqrt (dt) * gen.nextDouble(); path[observationIndex] = x; return x; } /** * Generates and returns an observation of the process * in dt time units, * assuming that the process has value x at the current time. * Uses the process parameters specified in the constructor. * Note that this method does not affect the sample path of the process * stored internally (if any). * */ public double nextObservation (double x, double dt) { x = x + alpha * (beta - x) * dt + sigma * Math.sqrt (dt) * gen.nextDouble(); return x; } /** * Generates a sample path of the process at all observation times, * which are provided in array t. * Note that t[0] should be the observation time of x0, * the initial value of the process, and t[] should have at least d + 1 * elements (see the setObservationTimes method). * */ public double[] generatePath() { double x; double xOld = x0; for (int j = 0; j < d; j++) { x = xOld + (beta - xOld)*alphadt[j] + sigmasqrdt[j]*gen.nextDouble(); path[j + 1] = x; xOld = x; } observationIndex = d; return path; } protected void initArrays(int d) { double dt; for (int j = 0; j < d; j++) { dt = t[j+1] - t[j]; alphadt[j] = alpha * (dt); sigmasqrdt[j] = sigma * Math.sqrt (dt); } } }

Ads help maintain this website.