chainladder.Triangle

Contents

chainladder.Triangle#

class chainladder.Triangle(data: DataFrame | DataFrameXchg | dict | None = None, origin: str | list | None = None, development: str | list | None = None, columns: str | list | None = None, index: str | list | None = None, origin_format: str | None = None, development_format: str | None = None, cumulative: bool | None = None, array_backend: str = None, pattern=False, trailing: bool = True, *args, **kwargs)[source]#

The core data structure of the chainladder package

Parameters:
data: DataFrame or DataFrameXchg, or dict

A single dataframe that contains columns representing all other arguments to the Triangle constructor. If using pandas version > 1.5.2, one may supply a DataFrame-like object (referred to as DataFrameXchg) supporting the __dataframe__ protocol, which will then be converted to a pandas DataFrame. If supplying a dict, it must be structured such that a pandas DataFrame created from it will be accepted by the constructor.

origin: str or list

A representation of the accident, reporting or more generally the origin period of the triangle that will map to the Origin dimension

development: str or list

A representation of the development/valuation periods of the triangle that will map to the Development dimension

columns: str or list

A representation of the numeric data of the triangle that will map to the columns dimension. If None, then a single ‘Total’ key will be generated.

index: str or list or None

A representation of the index of the triangle that will map to the index dimension. If None, then a single ‘Total’ key will be generated.

origin_format: optional str

A string representation of the date format of the origin arg. If omitted then date format will be inferred by pandas.

development_format: optional str

A string representation of the date format of the development arg. If omitted then date format will be inferred by pandas.

cumulative: bool

Whether the triangle is cumulative or incremental. This attribute is required to use the grain and dev_to_val methods and will be automatically set when invoking cum_to_incr or incr_to_cum methods.

trailing: bool

Controls how the period-end month is inferred from origin and development dates. When False, December is treated as the period end (i.e., calendar fiscal periods). When True, the period end is inferred from the data itself. This is useful when origin dates do not align with calendar period boundaries.

Attributes:
index: Series

Represents all available levels of the index dimension.

columns: Series

Represents all available levels of the value dimension.

origin: DatetimeIndex

Represents all available levels of the origin dimension.

development: Series

Represents all available levels of the development dimension.

key_labels: list

Represents the index axis labels

virtual_columns: Series

Represents the subset of columns of the triangle that are virtual.

valuation: DatetimeIndex

Represents all valuation dates of each cell in the Triangle.

origin_grain: str

The grain of the origin vector (‘Y’, ‘S’, ‘Q’, ‘M’)

development_grain: str

The grain of the development vector (‘Y’, ‘S’, ‘Q’, ‘M’)

shape: tuple

The 4D shape of the triangle instance with axes corresponding to (index, columns, origin, development)

link_ratio, age_to_age

Displays age-to-age ratios for the triangle.

valuation_datedate

The latest valuation date of the data

loc: Triangle

pandas-style loc accessor

iloc: Triangle

pandas-style iloc accessor

latest_diagonal: Triangle

The latest diagonal of the triangle

is_cumulative: bool

Whether the triangle is cumulative or not

is_ultimate: bool

Whether the triangle has an ultimate valuation

is_full: bool

Whether lower half of Triangle has been filled in

is_val_tri:

Whether the triangle development period is expressed as valuation periods.

values: array

4D numpy array underlying the Triangle instance

T: Triangle

Transpose index and columns of object. Only available when Triangle is convertible to DataFrame.

Methods

append(other)

Append rows of other to the end of caller, returning a new object.

astype(dtype[, inplace])

Copy of the array, cast to a specified type.

cum_to_incr([inplace])

Method to convert an cumlative triangle into a incremental triangle.

cumsum([axis])

Refer to pandas for cumsum functionality.

describe(*args, **kwargs)

Refer to pandas for describe functionality.

dev_to_val([inplace])

Converts triangle from a development lag triangle to a valuation triangle.

development_correlation([p_critical])

Mack (1997) test for correlations between subsequent development factors.

diff([axis])

Refer to pandas for diff functionality.

drop([labels, axis])

Drop specified labels from rows or columns.

drop_duplicates(*args, **kwargs)

Refer to pandas for drop_duplicates functionality.

dropna()

Method that removes origin/development vectors from edge of a triangle that are all missing values.

fillna([value, inplace])

Fill nan with 'value' by axis. Parameters ---------- value: single value or array-like values, default = None Value(s) to fill across the axis.

fillzero([inplace])

Fill nan with 0 by axis. separate function from fillna() because fillna(0) isn't working Parameters ---------- inplace: boolean, default = False Whether to modify the triangle object directly (True), or return a new modified triangle (False).

get_array_module([arr])

Returns the module pertaining to the backend underlying the supplied array.

grain([grain, trailing, inplace])

Changes the grain of a cumulative triangle.

groupby(by[, axis])

Group Triangle by index values.

heatmap([cmap, low, high, axis, subset])

Color the background in a gradient according to the data in each column (optionally row).

hvplot(*args, **kwargs)

Passthrough of pandas functionality

incr_to_cum([inplace])

Method to convert an incremental triangle into a cumulative triangle.

max([axis])

Refer to pandas for max functionality.

mean([axis])

Refer to pandas for mean functionality.

median([axis])

Refer to pandas for median functionality.

melt(*args, **kwargs)

Refer to pandas for melt functionality.

min([axis])

Refer to pandas for min functionality.

pct_chg(*args, **kwargs)

Refer to pandas for pct_chg functionality.

pivot(*args, **kwargs)

Refer to pandas for pivot functionality.

plot(*args, **kwargs)

Passthrough of pandas functionality

prod([axis])

Refer to pandas for prod functionality.

quantile([axis])

Refer to pandas for quantile functionality.

rename(axis, value)

Alter axes labels.

set_backend(backend[, inplace, deep])

Converts triangle array_backend.

set_index(value[, inplace])

Sets the index of the Triangle

shift([periods, axis])

Shift elements along an axis by desired number of periods.

sort_axis(axis)

Method to sort a Triangle along a given axis

std([axis])

Refer to pandas for std functionality.

sum([axis])

Refer to pandas for sum functionality.

to_clipboard(*args, **kwargs)

Refer to pandas for to_clipboard functionality.

to_csv(*args, **kwargs)

Refer to pandas for to_csv functionality.

to_dict(*args, **kwargs)

Refer to pandas for to_dict functionality.

to_excel(*args, **kwargs)

Refer to pandas for to_excel functionality.

to_frame([origin_as_datetime, keepdims, ...])

Converts a triangle to a pandas.DataFrame. Parameters ---------- origin_as_datetime : bool Whether the origin vector should be converted from PeriodIndex into a datetime dtype. Default is False. keepdims : bool If True, the triangle will be converted to a DataFrame with all dimensions intact. The argument will force a consistent DataFrame format regardless of whether any dimensions are of length 1. implicit_axis : bool When keepdims is True, this denotes whether to include the implicit valuation axis in addition to the origin and development. Returns ------- DataFrame or Series representation of the Triangle.

to_html(*args, **kwargs)

Refer to pandas for to_html functionality.

to_json()

Serializes triangle object to json format

to_pickle(path[, protocol])

Serializes triangle object to pickle.

trend([trend, axis, start, end, ultimate_lag])

Allows for the trending of a Triangle object along either a valuation or origin axis.

unstack(*args, **kwargs)

Refer to pandas for unstack functionality.

val_to_dev([inplace])

Converts triangle from a valuation triangle to a development lag triangle.

valuation_correlation([p_critical, total])

Mack test for calendar year effect A calendar period has impact across developments if the probability of the number of small (or large) development factors in that period occurring randomly is less than p_critical

var([axis])

Refer to pandas for var functionality.

broadcast_axis

compute

copy

exp

head

log

maximum

minimum

pipe

reindex

round

sort_index

sqrt

tail

Examples

Constructing a Triangle from a Pandas DataFrame.

import pandas as pd
df = pd.DataFrame(
    data={
        'origin': [1981, 1981, 1981, 1981, 1982, 1982, 1982, 1983, 1983, 1984],
        'development': [1981, 1982, 1983, 1984, 1982, 1983, 1984, 1983, 1984, 1984],
        'reported': [5012, 8269, 10907, 11805, 106, 4285, 5396, 3410, 8992, 5655],
    }
)
tr = cl.Triangle(
    data=df,
    origin='origin',
    development='development',
    columns=['reported'],
    cumulative=True,
)
print(tr)
          12      24       36       48
1981  5012.0  8269.0  10907.0  11805.0
1982   106.0  4285.0   5396.0      NaN
1983  3410.0  8992.0      NaN      NaN
1984  5655.0     NaN      NaN      NaN

When another dimension is added, such as an additional column, the Triangle becomes multidimensional. In this case, printing displays the Triangle’s metadata rather than its contents.

df = pd.DataFrame(
    data={
        'origin': [1981, 1981, 1981, 1981, 1982, 1982, 1982, 1983, 1983, 1984],
        'development': [1981, 1982, 1983, 1984, 1982, 1983, 1984, 1983, 1984, 1984],
        'reported': [5012, 8269, 10907, 11805, 106, 4285, 5396, 3410, 8992, 5655],
        'paid': [2506, 4135, 5454, 5903, 53, 2143, 2698, 1705, 4496, 2828],
    }
)
tr = cl.Triangle(
    data=df,
    origin='origin',
    development='development',
    columns=['reported', 'paid'],
    cumulative=True,
)
print(tr)
            Triangle Summary
Valuation:           1984-12
Grain:                  OYDY
Shape:          (1, 2, 4, 4)
Index:               [Total]
Columns:    [reported, paid]

Using the index parameter creates a multi-dimensional Triangle split by a categorical grouping, for example Line of Business.

df = pd.DataFrame(
    data={
         'lob': ['auto', 'auto', 'auto', 'home', 'home', 'home'],
        'origin': [2020, 2020, 2021, 2020, 2020, 2021],
        'development': [2020, 2021, 2021, 2020, 2021, 2021],
        'reported': [100, 150, 80, 200, 280, 160],
    }
)
tr = cl.Triangle(
    data=df,
    origin='origin',
    development='development',
    columns=['reported'],
    index=['lob'],
    cumulative=True,
)
print(tr)
           Triangle Summary
Valuation:          2021-12
Grain:                 OYDY
Shape:         (2, 1, 2, 2)
Index:                [lob]
Columns:         [reported]

Non-standard date strings can be parsed by specifying origin_format and development_format using Python strftime codes.

df = pd.DataFrame(
    data={
        'origin': ['2020-01', '2020-01', '2020-02', '2020-02'],
        'development': ['2020-01', '2020-02', '2020-02', '2020-03'],
        'reported': [100, 150, 200, 280],
    }
)
tr = cl.Triangle(
    data=df,
    origin='origin',
    origin_format='%Y-%m',
    development='development',
    development_format='%Y-%m',
    columns=['reported'],
    cumulative=True,
)
print(tr)
             1      2   3
2020-01  100.0  150.0 NaN
2020-02  200.0  280.0 NaN
2020-03    NaN    NaN NaN

Setting cumulative=False builds an incremental Triangle, where each cell is the amount accrued within that development period rather than the cumulative total to date.

df = pd.DataFrame(
    data={
        'origin': [1981, 1981, 1981, 1981, 1982, 1982, 1982, 1983, 1983, 1984],
        'development': [1981, 1982, 1983, 1984, 1982, 1983, 1984, 1983, 1984, 1984],
        'reported': [5012, 3257, 2638, 898, 106, 4179, 1111, 3410, 5582, 5655],
    }
)
tr = cl.Triangle(
    data=df,
    origin='origin',
    development='development',
    columns=['reported'],
    cumulative=False,
)
print(tr)
          12      24      36     48
1981  5012.0  3257.0  2638.0  898.0
1982   106.0  4179.0  1111.0    NaN
1983  3410.0  5582.0     NaN    NaN
1984  5655.0     NaN     NaN    NaN

By default (trailing=False), chainladder uses December as the fiscal period end, so origin dates are assigned to calendar quarters. Setting trailing=True instead infers the period end from the data itself, producing quarters aligned to the origin dates.

df = pd.DataFrame(
    data={
        'origin': ['2023-05', '2023-08', '2023-11', '2024-02'],
        'development': ['2024-04', '2024-04', '2024-04', '2024-04'],
        'premium': [100, 130, 160, 140],
    }
)
tr = cl.Triangle(
    data=df,
    origin='origin',
    origin_format='%Y-%m',
    development='development',
    development_format='%Y-%m',
    columns=['premium'],
    cumulative=True,
    trailing=False,
)
print(tr)
        2024-04
2023Q2    100.0
2023Q3    130.0
2023Q4    160.0
2024Q1    140.0
2024Q2      NaN
tr = cl.Triangle(
    data=df,
    origin='origin',
    origin_format='%Y-%m',
    development='development',
    development_format='%Y-%m',
    columns=['premium'],
    cumulative=True,
    trailing=True,
)
print(tr)
        2024Q2
2024Q1   100.0
2024Q2   130.0
2024Q3   160.0
2024Q4   140.0