# Vector of random variables, i.e. distributions

DistributionVectors.AbstractDistributionVectorType
AbstractDistributionVector{D <: Distribution}

Is any type able represent a vector of distribution of the same type. This corresponds to a sequence of random variables, each characterized by the same type of distribution but with different parameters. This allows aggregating functions to work, for example, computing the distribution of the sum of random variables by sum(dv::AbstractDistributionVector).

It is parametrized by D <: Distribution defining the type of the distribution used for all the random variables.

Items may be missing. Hence the element type of the iterator is Union{Missing,D}.

AbstractDistributionVector

• is iterable
• has length and index access, i.e. dv[i]::D
• access to entire parameter vectors: params(dv,Val(i))
• conversion to Tuple of Vectors: params(dv)
• array of random numbers: rand(n, dv): adding one dimension that represents across random variables
• query if entry is missing without needing to construct the distribution entry: ismissing(dv,i):

Specific implementations, need to implement at minimum methods length and getindex, and params.

There are two standard implementations:

Examples

import LinearAlgebra: I
dmn1 = MvNormal([0,0,0], 1 * I)
dmn2 = MvNormal([1,1,1], 2 * I)
dv = SimpleDistributionVector(dmn1, dmn2, missing, missing);
sample = rand(dv,2);
# 4 distr, each 2 samples of length 3
size(sample) == (3,2,4)
DistributionVectors.SimpleDistributionVectorType
SimpleDistributionVector{D <: Distribution, V}

Is an Vector-of-Distribution based implementation of AbstractDistributionVector.

Vector of random var can be created by

• specifying the distributions as arguments.
d1 = LogNormal(log(110), 0.25)
d2 = LogNormal(log(100), 0.15)
dv = SimpleDistributionVector(d1, d2, missing);
isequal(params(dv, Val(1)), [log(110), log(100), missing])
• providing the Type of distribution and vectors of each parameter
mu = [1.1,1.2,1.3]
sigma = [1.01, 1.02, missing]
dv = SimpleDistributionVector(LogNormal{eltype(mu)}, mu, sigma);
isequal(params(dv, Val(1)), [1.1,1.2,missing])

Note that if one of the parameters is missing, then the entire entry of the distribution is marked missing.

Since Distributions are stored directly, indexing passes a reference. However, getting parameter vectors, required iterating all distributions, and allocating a new vector.

DistributionVectors.ParamDistributionVectorType
ParamDistributionVector{D <: Distribution, V}

Is an Tuple of Vectors based implementation of AbstractDistributionVector.

Vector of random var can be created by

• specifying the distributions as arguments with some overhead of converting the Distributions to vectors of each parameter
d1 = LogNormal(log(110), 0.25)
d2 = LogNormal(log(100), 0.15)
dv = ParamDistributionVector(d1, d2, missing);
isequal(params(dv, Val(1)), [log(110), log(100), missing])
• providing the Type of distribution and vectors of each parameter
mu = [1.1,1.2,1.3]
sigma = [1.01, 1.02, missing]
dv = ParamDistributionVector(LogNormal{eltype(mu)}, mu, sigma);
ismissing(dv[3])
isequal(params(dv, Val(1)), [1.1,1.2,1.3]) # third still not missing here

Note that if one of the parameters for entry i is missing, then dv[i] is missing.

Since distributions are stored by parameter vectors, the acces to these vectors is just passing a reference. Indexing, will create Distribution types.

## Helpers

The conversion between a missing-allowed vector of parameter tuples to a tuple of vectors for each parameter (as used by ParamDistributionVector) is provided in a type-stable manner by function vectuptotupvec.

DistributionVectors.vectuptotupvecFunction
vectuptotupvec(vectup)

Typesafe convert from Vector of Tuples to Tuple of Vectors.

Arguments

• vectup: A Vector of identical Tuples

Examples

vectup = [(1,1.01, "string 1"), (2,2.02, "string 2")]
vectuptotupvec(vectup) == ([1, 2], [1.01, 2.02], ["string 1", "string 2"])