com.opengamma.strata.calc.Column Maven / Gradle / Ivy
Show all versions of strata-calc Show documentation
/*
* Copyright (C) 2015 - present by OpenGamma Inc. and the OpenGamma group of companies
*
* Please see distribution for license.
*/
package com.opengamma.strata.calc;
import java.util.Map;
import java.util.NoSuchElementException;
import java.util.Optional;
import org.joda.beans.Bean;
import org.joda.beans.ImmutableBean;
import org.joda.beans.JodaBeanUtils;
import org.joda.beans.MetaBean;
import org.joda.beans.MetaProperty;
import org.joda.beans.gen.BeanDefinition;
import org.joda.beans.gen.ImmutableDefaults;
import org.joda.beans.gen.ImmutablePreBuild;
import org.joda.beans.gen.PropertyDefinition;
import org.joda.beans.impl.direct.DirectFieldsBeanBuilder;
import org.joda.beans.impl.direct.DirectMetaBean;
import org.joda.beans.impl.direct.DirectMetaProperty;
import org.joda.beans.impl.direct.DirectMetaPropertyMap;
import com.opengamma.strata.basics.currency.Currency;
import com.opengamma.strata.calc.runner.CalculationParameter;
import com.opengamma.strata.calc.runner.CalculationParameters;
/**
* Defines a column in a set of calculation results.
*
* {@link CalculationRunner} provides the ability to calculate a grid of results
* for a given set targets and columns. This class is used to define the columns.
*
* A column is defined in terms of a unique name, measure to be calculated and
* a set of parameters that control the calculation. The functions to invoke
* and the default set of parameters are defined on {@link CalculationRules}.
*/
@BeanDefinition
public final class Column implements ImmutableBean {
/**
* The column name.
*
* This is the name of the column, and should be unique in a list of columns.
*/
@PropertyDefinition(validate = "notNull")
private final ColumnName name;
/**
* The measure to be calculated.
*
* This defines the calculation being performed, such as 'PresentValue' or 'ParRate'.
*/
@PropertyDefinition(validate = "notNull")
private final Measure measure;
/**
* The reporting currency, used to control currency conversion, optional.
*
* This is used to specify the currency that the result should be reporting in.
* If the result is not associated with a currency, such as for "par rate", then the
* reporting currency will effectively be ignored.
*
* If empty, the reporting currency from {@link CalculationRules} will be used.
*/
@PropertyDefinition(get = "optional")
private final ReportingCurrency reportingCurrency;
/**
* The calculation parameters that apply to this column, used to control the how the calculation is performed.
*
* The parameters from {@link CalculationRules} and {@code Column} are combined.
* If a parameter is defined here and in the rules with the same
* {@linkplain CalculationParameter#queryType() query type}, then the column parameter takes precedence.
*
* When building, these will default to be empty.
*/
@PropertyDefinition
private final CalculationParameters parameters;
//-------------------------------------------------------------------------
/**
* Obtains an instance that will calculate the specified measure.
*
* The column name will be the same as the name of the measure.
* No calculation parameters are provided, thus the parameters from {@link CalculationRules} will be used.
* Currency conversion is controlled by the reporting currency in {@code CalculationRules}.
*
* @param measure the measure to be calculated
* @return a column with the specified measure
*/
public static Column of(Measure measure) {
ColumnName name = ColumnName.of(measure);
return new Column(name, measure, null, CalculationParameters.empty());
}
/**
* Obtains an instance that will calculate the specified measure, converting to the specified currency.
*
* The column name will be the same as the name of the measure.
*
* @param measure the measure to be calculated
* @param currency the currency to convert to
* @return a column with the specified measure
*/
public static Column of(Measure measure, Currency currency) {
ColumnName name = ColumnName.of(measure);
return new Column(name, measure, ReportingCurrency.of(currency), CalculationParameters.empty());
}
/**
* Obtains an instance that will calculate the specified measure, defining additional parameters.
*
* The column name will be the same as the name of the measure.
* The specified calculation parameters take precedence over those in {@link CalculationRules},
* with the combined set being used for the column.
* Currency conversion is controlled by the reporting currency in {@code CalculationRules}.
*
* @param measure the measure to be calculated
* @param parameters the parameters that control the calculation, may be empty
* @return a column with the specified measure and reporting currency
*/
public static Column of(Measure measure, CalculationParameter... parameters) {
ColumnName name = ColumnName.of(measure);
return new Column(name, measure, null, CalculationParameters.of(parameters));
}
/**
* Obtains an instance that will calculate the specified measure, converting to the specified currency,
* defining additional parameters.
*
* The column name will be the same as the name of the measure.
* The specified calculation parameters take precedence over those in {@link CalculationRules},
* with the combined set being used for the column.
*
* @param measure the measure to be calculated
* @param currency the currency to convert to
* @param parameters the parameters that control the calculation, may be empty
* @return a column with the specified measure and reporting currency
*/
public static Column of(Measure measure, Currency currency, CalculationParameter... parameters) {
ColumnName name = ColumnName.of(measure);
return new Column(name, measure, ReportingCurrency.of(currency), CalculationParameters.of(parameters));
}
/**
* Obtains an instance that will calculate the specified measure, defining the column name.
*
* No calculation parameters are provided, thus the parameters from {@link CalculationRules} will be used.
* Currency conversion is controlled by the reporting currency in {@code CalculationRules}.
*
* @param measure the measure to be calculated
* @param columnName the column name
* @return a column with the specified measure and column name
*/
public static Column of(Measure measure, String columnName) {
ColumnName name = ColumnName.of(columnName);
return new Column(name, measure, null, CalculationParameters.empty());
}
/**
* Obtains an instance that will calculate the specified measure, converting to the specified currency.
*
* The specified currency will be wrapped in {@link ReportingCurrency} and added to the calculation parameters.
*
* @param measure the measure to be calculated
* @param columnName the column name
* @param currency the currency to convert to
* @return a column with the specified measure
*/
public static Column of(Measure measure, String columnName, Currency currency) {
ColumnName name = ColumnName.of(columnName);
return new Column(name, measure, ReportingCurrency.of(currency), CalculationParameters.empty());
}
/**
* Obtains an instance that will calculate the specified measure, defining the column name and parameters.
*
* The specified calculation parameters take precedence over those in {@link CalculationRules},
* with the combined set being used for the column.
* Currency conversion is controlled by the reporting currency in {@code CalculationRules}.
*
* @param measure the measure to be calculated
* @param columnName the column name
* @param parameters the parameters that control the calculation, may be empty
* @return a column with the specified measure, column name and reporting currency
*/
public static Column of(
Measure measure,
String columnName,
CalculationParameter... parameters) {
ColumnName name = ColumnName.of(columnName);
return new Column(name, measure, null, CalculationParameters.of(parameters));
}
/**
* Obtains an instance that will calculate the specified measure, converting to the specified currency,
* defining the column name and parameters.
*
* The specified calculation parameters take precedence over those in {@link CalculationRules},
* with the combined set being used for the column.
*
* @param measure the measure to be calculated
* @param columnName the column name
* @param currency the currency to convert to
* @param parameters the parameters that control the calculation, may be empty
* @return a column with the specified measure, column name and reporting currency
*/
public static Column of(
Measure measure,
String columnName,
Currency currency,
CalculationParameter... parameters) {
ColumnName name = ColumnName.of(columnName);
return new Column(name, measure, ReportingCurrency.of(currency), CalculationParameters.of(parameters));
}
@ImmutableDefaults
private static void applyDefaults(Builder builder) {
builder.parameters(CalculationParameters.empty());
}
@ImmutablePreBuild
private static void preBuild(Builder builder) {
if (builder.name == null && builder.measure != null) {
builder.name(ColumnName.of(builder.measure.getName()));
}
}
//-------------------------------------------------------------------------
/**
* Combines the parameters with another reporting currency and set of parameters.
*
* @param reportingCurrency the default reporting currency
* @param defaultParameters the default parameters
* @return the combined column
*/
public Column combineWithDefaults(ReportingCurrency reportingCurrency, CalculationParameters defaultParameters) {
CalculationParameters combinedParams = parameters.combinedWith(defaultParameters);
return new Column(name, measure, getReportingCurrency().orElse(reportingCurrency), combinedParams);
}
/**
* Converts this column to a column header.
*
* The header is a reduced form of the column used in {@link Results}.
*
* @return the column header
*/
public ColumnHeader toHeader() {
if (measure.isCurrencyConvertible()) {
ReportingCurrency reportingCurrency = getReportingCurrency().orElse(ReportingCurrency.NATURAL);
if (reportingCurrency.isSpecific()) {
return ColumnHeader.of(name, measure, reportingCurrency.getCurrency());
}
}
return ColumnHeader.of(name, measure);
}
//------------------------- AUTOGENERATED START -------------------------
/**
* The meta-bean for {@code Column}.
* @return the meta-bean, not null
*/
public static Column.Meta meta() {
return Column.Meta.INSTANCE;
}
static {
MetaBean.register(Column.Meta.INSTANCE);
}
/**
* Returns a builder used to create an instance of the bean.
* @return the builder, not null
*/
public static Column.Builder builder() {
return new Column.Builder();
}
private Column(
ColumnName name,
Measure measure,
ReportingCurrency reportingCurrency,
CalculationParameters parameters) {
JodaBeanUtils.notNull(name, "name");
JodaBeanUtils.notNull(measure, "measure");
this.name = name;
this.measure = measure;
this.reportingCurrency = reportingCurrency;
this.parameters = parameters;
}
@Override
public Column.Meta metaBean() {
return Column.Meta.INSTANCE;
}
//-----------------------------------------------------------------------
/**
* Gets the column name.
*
* This is the name of the column, and should be unique in a list of columns.
* @return the value of the property, not null
*/
public ColumnName getName() {
return name;
}
//-----------------------------------------------------------------------
/**
* Gets the measure to be calculated.
*
* This defines the calculation being performed, such as 'PresentValue' or 'ParRate'.
* @return the value of the property, not null
*/
public Measure getMeasure() {
return measure;
}
//-----------------------------------------------------------------------
/**
* Gets the reporting currency, used to control currency conversion, optional.
*
* This is used to specify the currency that the result should be reporting in.
* If the result is not associated with a currency, such as for "par rate", then the
* reporting currency will effectively be ignored.
*
* If empty, the reporting currency from {@link CalculationRules} will be used.
* @return the optional value of the property, not null
*/
public Optional getReportingCurrency() {
return Optional.ofNullable(reportingCurrency);
}
//-----------------------------------------------------------------------
/**
* Gets the calculation parameters that apply to this column, used to control the how the calculation is performed.
*
* The parameters from {@link CalculationRules} and {@code Column} are combined.
* If a parameter is defined here and in the rules with the same
* {@linkplain CalculationParameter#queryType() query type}, then the column parameter takes precedence.
*
* When building, these will default to be empty.
* @return the value of the property
*/
public CalculationParameters getParameters() {
return parameters;
}
//-----------------------------------------------------------------------
/**
* Returns a builder that allows this bean to be mutated.
* @return the mutable builder, not null
*/
public Builder toBuilder() {
return new Builder(this);
}
@Override
public boolean equals(Object obj) {
if (obj == this) {
return true;
}
if (obj != null && obj.getClass() == this.getClass()) {
Column other = (Column) obj;
return JodaBeanUtils.equal(name, other.name) &&
JodaBeanUtils.equal(measure, other.measure) &&
JodaBeanUtils.equal(reportingCurrency, other.reportingCurrency) &&
JodaBeanUtils.equal(parameters, other.parameters);
}
return false;
}
@Override
public int hashCode() {
int hash = getClass().hashCode();
hash = hash * 31 + JodaBeanUtils.hashCode(name);
hash = hash * 31 + JodaBeanUtils.hashCode(measure);
hash = hash * 31 + JodaBeanUtils.hashCode(reportingCurrency);
hash = hash * 31 + JodaBeanUtils.hashCode(parameters);
return hash;
}
@Override
public String toString() {
StringBuilder buf = new StringBuilder(160);
buf.append("Column{");
buf.append("name").append('=').append(JodaBeanUtils.toString(name)).append(',').append(' ');
buf.append("measure").append('=').append(JodaBeanUtils.toString(measure)).append(',').append(' ');
buf.append("reportingCurrency").append('=').append(JodaBeanUtils.toString(reportingCurrency)).append(',').append(' ');
buf.append("parameters").append('=').append(JodaBeanUtils.toString(parameters));
buf.append('}');
return buf.toString();
}
//-----------------------------------------------------------------------
/**
* The meta-bean for {@code Column}.
*/
public static final class Meta extends DirectMetaBean {
/**
* The singleton instance of the meta-bean.
*/
static final Meta INSTANCE = new Meta();
/**
* The meta-property for the {@code name} property.
*/
private final MetaProperty name = DirectMetaProperty.ofImmutable(
this, "name", Column.class, ColumnName.class);
/**
* The meta-property for the {@code measure} property.
*/
private final MetaProperty measure = DirectMetaProperty.ofImmutable(
this, "measure", Column.class, Measure.class);
/**
* The meta-property for the {@code reportingCurrency} property.
*/
private final MetaProperty reportingCurrency = DirectMetaProperty.ofImmutable(
this, "reportingCurrency", Column.class, ReportingCurrency.class);
/**
* The meta-property for the {@code parameters} property.
*/
private final MetaProperty parameters = DirectMetaProperty.ofImmutable(
this, "parameters", Column.class, CalculationParameters.class);
/**
* The meta-properties.
*/
private final Map> metaPropertyMap$ = new DirectMetaPropertyMap(
this, null,
"name",
"measure",
"reportingCurrency",
"parameters");
/**
* Restricted constructor.
*/
private Meta() {
}
@Override
protected MetaProperty> metaPropertyGet(String propertyName) {
switch (propertyName.hashCode()) {
case 3373707: // name
return name;
case 938321246: // measure
return measure;
case -1287844769: // reportingCurrency
return reportingCurrency;
case 458736106: // parameters
return parameters;
}
return super.metaPropertyGet(propertyName);
}
@Override
public Column.Builder builder() {
return new Column.Builder();
}
@Override
public Class extends Column> beanType() {
return Column.class;
}
@Override
public Map> metaPropertyMap() {
return metaPropertyMap$;
}
//-----------------------------------------------------------------------
/**
* The meta-property for the {@code name} property.
* @return the meta-property, not null
*/
public MetaProperty name() {
return name;
}
/**
* The meta-property for the {@code measure} property.
* @return the meta-property, not null
*/
public MetaProperty measure() {
return measure;
}
/**
* The meta-property for the {@code reportingCurrency} property.
* @return the meta-property, not null
*/
public MetaProperty reportingCurrency() {
return reportingCurrency;
}
/**
* The meta-property for the {@code parameters} property.
* @return the meta-property, not null
*/
public MetaProperty parameters() {
return parameters;
}
//-----------------------------------------------------------------------
@Override
protected Object propertyGet(Bean bean, String propertyName, boolean quiet) {
switch (propertyName.hashCode()) {
case 3373707: // name
return ((Column) bean).getName();
case 938321246: // measure
return ((Column) bean).getMeasure();
case -1287844769: // reportingCurrency
return ((Column) bean).reportingCurrency;
case 458736106: // parameters
return ((Column) bean).getParameters();
}
return super.propertyGet(bean, propertyName, quiet);
}
@Override
protected void propertySet(Bean bean, String propertyName, Object newValue, boolean quiet) {
metaProperty(propertyName);
if (quiet) {
return;
}
throw new UnsupportedOperationException("Property cannot be written: " + propertyName);
}
}
//-----------------------------------------------------------------------
/**
* The bean-builder for {@code Column}.
*/
public static final class Builder extends DirectFieldsBeanBuilder {
private ColumnName name;
private Measure measure;
private ReportingCurrency reportingCurrency;
private CalculationParameters parameters;
/**
* Restricted constructor.
*/
private Builder() {
applyDefaults(this);
}
/**
* Restricted copy constructor.
* @param beanToCopy the bean to copy from, not null
*/
private Builder(Column beanToCopy) {
this.name = beanToCopy.getName();
this.measure = beanToCopy.getMeasure();
this.reportingCurrency = beanToCopy.reportingCurrency;
this.parameters = beanToCopy.getParameters();
}
//-----------------------------------------------------------------------
@Override
public Object get(String propertyName) {
switch (propertyName.hashCode()) {
case 3373707: // name
return name;
case 938321246: // measure
return measure;
case -1287844769: // reportingCurrency
return reportingCurrency;
case 458736106: // parameters
return parameters;
default:
throw new NoSuchElementException("Unknown property: " + propertyName);
}
}
@Override
public Builder set(String propertyName, Object newValue) {
switch (propertyName.hashCode()) {
case 3373707: // name
this.name = (ColumnName) newValue;
break;
case 938321246: // measure
this.measure = (Measure) newValue;
break;
case -1287844769: // reportingCurrency
this.reportingCurrency = (ReportingCurrency) newValue;
break;
case 458736106: // parameters
this.parameters = (CalculationParameters) newValue;
break;
default:
throw new NoSuchElementException("Unknown property: " + propertyName);
}
return this;
}
@Override
public Builder set(MetaProperty> property, Object value) {
super.set(property, value);
return this;
}
@Override
public Column build() {
preBuild(this);
return new Column(
name,
measure,
reportingCurrency,
parameters);
}
//-----------------------------------------------------------------------
/**
* Sets the column name.
*
* This is the name of the column, and should be unique in a list of columns.
* @param name the new value, not null
* @return this, for chaining, not null
*/
public Builder name(ColumnName name) {
JodaBeanUtils.notNull(name, "name");
this.name = name;
return this;
}
/**
* Sets the measure to be calculated.
*
* This defines the calculation being performed, such as 'PresentValue' or 'ParRate'.
* @param measure the new value, not null
* @return this, for chaining, not null
*/
public Builder measure(Measure measure) {
JodaBeanUtils.notNull(measure, "measure");
this.measure = measure;
return this;
}
/**
* Sets the reporting currency, used to control currency conversion, optional.
*
* This is used to specify the currency that the result should be reporting in.
* If the result is not associated with a currency, such as for "par rate", then the
* reporting currency will effectively be ignored.
*
* If empty, the reporting currency from {@link CalculationRules} will be used.
* @param reportingCurrency the new value
* @return this, for chaining, not null
*/
public Builder reportingCurrency(ReportingCurrency reportingCurrency) {
this.reportingCurrency = reportingCurrency;
return this;
}
/**
* Sets the calculation parameters that apply to this column, used to control the how the calculation is performed.
*
* The parameters from {@link CalculationRules} and {@code Column} are combined.
* If a parameter is defined here and in the rules with the same
* {@linkplain CalculationParameter#queryType() query type}, then the column parameter takes precedence.
*
* When building, these will default to be empty.
* @param parameters the new value
* @return this, for chaining, not null
*/
public Builder parameters(CalculationParameters parameters) {
this.parameters = parameters;
return this;
}
//-----------------------------------------------------------------------
@Override
public String toString() {
StringBuilder buf = new StringBuilder(160);
buf.append("Column.Builder{");
buf.append("name").append('=').append(JodaBeanUtils.toString(name)).append(',').append(' ');
buf.append("measure").append('=').append(JodaBeanUtils.toString(measure)).append(',').append(' ');
buf.append("reportingCurrency").append('=').append(JodaBeanUtils.toString(reportingCurrency)).append(',').append(' ');
buf.append("parameters").append('=').append(JodaBeanUtils.toString(parameters));
buf.append('}');
return buf.toString();
}
}
//-------------------------- AUTOGENERATED END --------------------------
}