All Downloads are FREE. Search and download functionalities are using the official Maven repository.

com.meliorbis.economics.individual.egm.EGMIndividualProblemSolverWithControls Maven / Gradle / Ivy

/**
 * 
 */
package com.meliorbis.economics.individual.egm;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;

import org.apache.commons.lang.ArrayUtils;

import com.meliorbis.economics.model.Model;
import com.meliorbis.economics.model.ModelConfig;
import com.meliorbis.economics.model.State;
import com.meliorbis.numerics.generic.primitives.DoubleArray;
import com.meliorbis.numerics.generic.primitives.impl.Interpolation.Params;
import com.meliorbis.utils.Utils;

/**
 * An Endogenous Grid Method Solver which supports controls affecting expectations and hence requires 
 * expectations to be calculated conditional on current control.
 * 
 * NOT WELL TESTED.
 * 
 * @author Tobias Grasl
 * 
 * @param  The Config type
 * @param  The State type
 * @param  The Model type
 */
public abstract class EGMIndividualProblemSolverWithControls, 
													M extends Model> 
												extends EGMSolverBase
{

	public EGMIndividualProblemSolverWithControls(M model_, C config_)
	{
		super(model_, config_);
		
		_interpParams = new Params().constrained(_config.isConstrained());
		
		final DoubleArray transitionProbabilities = _config.getExogenousStateTransition();

		/* Determine the size of the conditional expectations array in advance
		 */
		List fccDimensions = new ArrayList();

		/* IMPORTANT: Assumes the prior ind exo state is not relevant, i.e both markov property
		 * and that all the endo states are the same
		 */
		fccDimensions.addAll(Arrays.asList(ArrayUtils.toObject(
				ArrayUtils.subarray(transitionProbabilities.size(), _config.getIndividualExogenousStateCount(), 
						transitionProbabilities.numberOfDimensions()))));

		_firstAggStateDim = fccDimensions.size();

		Utils.addLengthsToList(fccDimensions, _config.getAggregateEndogenousStates());
		
		// Add the sizes of the controls which affect expectations
		for(int ctrlIdx : config_.getControlsAffectingExpectations())
		{
			fccDimensions.add(config_.getAggregateControls().get(ctrlIdx).numberOfElements());
		}
		
		_firstIndividualStateDim = fccDimensions.size();

		Utils.addLengthsToList(fccDimensions, _config.getIndividualEndogenousStates());

		fccDimensions.add(getNumberOfIndividualExpectations());
		
		_futureConditionalContribsSize = Utils.toIntArray(fccDimensions);
		
		final int nIndShocks = _config.getIndividualExogenousStateCount();
		final int nIndStates = _config.getIndividualEndogenousStateCount();
		
		final int nAggShocks = _config.getAggregateExogenousStateCount();	
		final int nAggStates = _config.getAggregateEndogenousStateCount();
		final int nAggControls = _config.getAggregateControlCount();
		
		_arrangeIndexs = Utils.combine(
				// First the individual endo states, which are at the end of the fcc
				// array. NOTE: Just using efc as a convenience since we are extracting
				// from
				// the (equal length) subindex
						Utils.sequence( nAggShocks + nAggStates + _config.getControlsAffectingExpectations().length, nAggShocks + nAggStates + _config.getControlsAffectingExpectations().length + nIndStates),
						// Then the aggregate states and controls, which are in the
						// subindex where the future shocks are in the full index
						Utils.sequence(nAggShocks, nAggShocks+nAggStates + _config.getControlsAffectingExpectations().length),
						// Then the agg exo states
						Utils.sequence(0, nAggShocks),
						// Leave the one at the end which differentiates the variables,
						new int[] {nAggShocks+nIndStates+nAggStates + _config.getControlsAffectingExpectations().length,
							});
		
		
		// If there are aggregate controls...
		if( nAggControls > 0  && _config.getControlsAffectingExpectations().length < nAggControls) 
		{	
			// Ind shocks are missing due to fillAt, and the controls are the dimensions we need to expand to
			_acrossDims = Utils.sequence(0, nIndStates + nAggStates);
			
			for(int ctrlIndex : _config.getControlsAffectingExpectations())
			{
				_acrossDims = ArrayUtils.add(_acrossDims, nIndStates + nAggStates + ctrlIndex);
			}
								
			_acrossDims = Utils.combine(_acrossDims, Utils.sequence(nIndStates + nAggStates + nAggControls,
					model_.createIndividualVariableGrid().numberOfDimensions()-nIndShocks));
		}
	}

}




© 2015 - 2025 Weber Informatics LLC | Privacy Policy