Пример #1
0
def test_grid():
    # Load Data
    clrd = cl.load_sample("clrd")
    medmal_paid = clrd.groupby("LOB").sum().loc["medmal"]["CumPaidLoss"]
    medmal_prem = (clrd.groupby("LOB").sum().loc["medmal"]
                   ["EarnedPremDIR"].latest_diagonal)
    medmal_prem.rename("development", ["premium"])

    # Pipeline
    dev = cl.Development()
    tail = cl.TailCurve()
    benk = cl.Benktander()

    steps = [("dev", dev), ("tail", tail), ("benk", benk)]
    pipe = cl.Pipeline(steps)

    # Prep Benktander Grid Search with various assumptions, and a scoring function
    param_grid = dict(benk__n_iters=[250], benk__apriori=[1.00])
    scoring = {"IBNR": lambda x: x.named_steps.benk.ibnr_.sum()}

    grid = cl.GridSearch(pipe, param_grid, scoring=scoring)
    # Perform Grid Search
    grid.fit(medmal_paid, benk__sample_weight=medmal_prem)
    assert (grid.results_["IBNR"][0] == cl.Benktander(
        n_iters=250, apriori=1).fit(
            cl.TailCurve().fit_transform(
                cl.Development().fit_transform(medmal_paid)),
            sample_weight=medmal_prem,
        ).ibnr_.sum())
Пример #2
0
def test_grid():
    # Load Data
    clrd = cl.load_dataset('clrd')
    medmal_paid = clrd.groupby('LOB').sum().loc['medmal']['CumPaidLoss']
    medmal_prem = clrd.groupby(
        'LOB').sum().loc['medmal']['EarnedPremDIR'].latest_diagonal
    medmal_prem.rename('development', ['premium'])

    # Pipeline
    dev = cl.Development()
    tail = cl.TailCurve()
    benk = cl.Benktander()

    steps = [('dev', dev), ('tail', tail), ('benk', benk)]
    pipe = cl.Pipeline(steps)

    # Prep Benktander Grid Search with various assumptions, and a scoring function
    param_grid = dict(benk__n_iters=[250], benk__apriori=[1.00])
    scoring = {'IBNR': lambda x: x.named_steps.benk.ibnr_.sum()[0]}

    grid = cl.GridSearch(pipe, param_grid, scoring=scoring)
    # Perform Grid Search
    grid.fit(medmal_paid, benk__sample_weight=medmal_prem)
    assert grid.results_['IBNR'][0] == \
        cl.Benktander(n_iters=250, apriori=1).fit(cl.TailCurve().fit_transform(cl.Development().fit_transform(medmal_paid)), sample_weight=medmal_prem).ibnr_.sum()[0]
Пример #3
0
def test_pipeline():
    tri = cl.load_sample('clrd').groupby('LOB').sum()[[
        'CumPaidLoss', 'IncurLoss', 'EarnedPremDIR'
    ]]
    tri['CaseIncurredLoss'] = tri['IncurLoss'] - tri['CumPaidLoss']

    X = tri[['CumPaidLoss', 'CaseIncurredLoss']]
    sample_weight = tri['EarnedPremDIR'].latest_diagonal

    dev = [
        cl.Development(),
        cl.ClarkLDF(),
        cl.Trend(),
        cl.IncrementalAdditive(),
        cl.MunichAdjustment(paid_to_incurred=('CumPaidLoss',
                                              'CaseIncurredLoss')),
        cl.CaseOutstanding(paid_to_incurred=('CumPaidLoss',
                                             'CaseIncurredLoss'))
    ]
    tail = [cl.TailCurve(), cl.TailConstant(), cl.TailBondy(), cl.TailClark()]
    ibnr = [
        cl.Chainladder(),
        cl.BornhuetterFerguson(),
        cl.Benktander(n_iters=2),
        cl.CapeCod()
    ]

    for model in list(itertools.product(dev, tail, ibnr)):
        print(model)
        cl.Pipeline(
            steps=[('dev',
                    model[0]), ('tail',
                                model[1]), ('ibnr', model[2])]).fit_predict(
                                    X, sample_weight=sample_weight).ibnr_.sum(
                                        'origin').sum('columns').sum()
Пример #4
0
def test_fit_period():
    tri = cl.load_dataset('tail_sample')
    dev = cl.Development(average='simple').fit_transform(tri)
    assert round(
        cl.TailCurve(fit_period=slice(-6, None, None),
                     extrap_periods=10).fit(dev).cdf_['paid'].values[0, 0, 0,
                                                                     -2],
        3) == 1.044
def test_fit_period():
    tri = cl.load_sample('tail_sample')
    dev = cl.Development(average='simple').fit_transform(tri)
    assert round(
        cl.TailCurve(fit_period=(tri.ddims[-7], None),
                     extrap_periods=10).fit(dev).cdf_['paid'].set_backend(
                         'numpy', inplace=True).values[0, 0, 0, -2],
        3) == 1.044
def test_fit_period():
    tri = cl.load_sample("tail_sample")
    dev = cl.Development(average="simple").fit_transform(tri)
    assert (round(
        cl.TailCurve(fit_period=(tri.ddims[-7], None),
                     extrap_periods=10).fit(dev).cdf_["paid"].set_backend(
                         "numpy", inplace=True).values[0, 0, 0, -2],
        3,
    ) == 1.044)
Пример #7
0
def test_basic_transform(raa):
    cl.Development().fit_transform(raa)
    cl.ClarkLDF().fit_transform(raa)
    cl.TailClark().fit_transform(raa)
    cl.TailBondy().fit_transform(raa)
    cl.TailConstant().fit_transform(raa)
    cl.TailCurve().fit_transform(raa)
    cl.BootstrapODPSample().fit_transform(raa)
    cl.IncrementalAdditive().fit_transform(raa,
                                           sample_weight=raa.latest_diagonal)
def test_basic_transform():
    tri = cl.load_sample("raa")
    cl.Development().fit_transform(tri)
    cl.ClarkLDF().fit_transform(tri)
    cl.TailClark().fit_transform(tri)
    cl.TailBondy().fit_transform(tri)
    cl.TailConstant().fit_transform(tri)
    cl.TailCurve().fit_transform(tri)
    cl.BootstrapODPSample().fit_transform(tri)
    cl.IncrementalAdditive().fit_transform(tri,
                                           sample_weight=tri.latest_diagonal)
Пример #9
0
def mack_p(data, average, est_sigma, tail):
    if tail:
        return cl.MackChainladder().fit(
            cl.TailCurve(curve='exponential').fit_transform(
                cl.Development(average=average,
                               sigma_interpolation=est_sigma).fit_transform(
                                   cl.load_sample(data))))
    else:
        return cl.MackChainladder().fit(
            cl.Development(average=average,
                           sigma_interpolation=est_sigma).fit_transform(
                               cl.load_sample(data)))
===========================

This example demonstrates how you can slice triangle objects to perform a
typical 'Actual vs Expected' analysis.  We will use Medical Malpractice
payment patterns for the demo.
"""

import chainladder as cl

# Load the data
tri_1997 = cl.load_sample('clrd')
tri_1997 = tri_1997.groupby('LOB').sum().loc['medmal']['CumPaidLoss']

# Create a triangle as of the previous valuation and build IBNR model
tri_1996 = tri_1997[tri_1997.valuation < '1997']
model_1996 = cl.Chainladder().fit(cl.TailCurve().fit_transform(tri_1996))

# Slice the expected losses from the 1997 calendar period of the model
ave = model_1996.full_triangle_.dev_to_val()
ave = ave[ave.valuation == tri_1997.valuation_date].rename(
    'columns', 'Expected')

# Slice the actual losses from the 1997 calendar period for prior AYs
ave['Actual'] = tri_1997.latest_diagonal[tri_1997.origin < '1997']
ave['Actual - Expected'] = ave['Actual'] - ave['Expected']

# Plotting
ave.to_frame().T.plot(y='Actual - Expected',
                      kind='bar',
                      legend=False,
                      grid=True).set(title='Calendar Period 1997 Performance',
def mack_p(data, average, est_sigma):
    return cl.TailCurve(curve='exponential').fit_transform(cl.Development(average=average, sigma_interpolation=est_sigma).fit_transform(cl.load_dataset(data)))
Пример #12
0
"""
===============================
Attachment Age Smoothing
===============================

This simple example demonstrates how a Tail ``attachment_age`` can be used to
smooth over development patterns within the triangle.  Regardless of where
the ``attachment_age`` is set, the patterns will always extrapolate one year
past the highest known lag of the `Triangle` before applying a terminal tail
factor.

"""

import chainladder as cl
import pandas as pd

raa = cl.load_sample('raa')

pd.concat(
    (cl.TailCurve().fit(raa).ldf_.T.iloc[:, 0].rename('Unsmoothed'),
     cl.TailCurve(
         attachment_age=12).fit(raa).ldf_.T.iloc[:, 0].rename('Curve Fit')),
    1).plot(grid=True, title='Exponential Smoothing of LDF')
Пример #13
0
special case of the Benktander model where ``n_iters = 1`` for BornhuetterFerguson
and as ``n_iters`` approaches infinity yields the chainladder.  As ``n_iters``
increases the apriori selection becomes less relevant regardless of initial
choice.
"""
import chainladder as cl

# Load Data
clrd = cl.load_sample('clrd')
medmal_paid = clrd.groupby('LOB').sum().loc['medmal', 'CumPaidLoss']
medmal_prem = clrd.groupby('LOB').sum().loc['medmal', 'EarnedPremDIR'].latest_diagonal
medmal_prem.rename('development', ['premium'])

# Generate LDFs and Tail Factor
medmal_paid = cl.Development().fit_transform(medmal_paid)
medmal_paid = cl.TailCurve().fit_transform(medmal_paid)

# Benktander Model
benk = cl.Benktander()

# Prep Benktander Grid Search with various assumptions, and a scoring function
param_grid = dict(n_iters=list(range(1,100,2)),
                  apriori=[0.50, 0.75, 1.00])
scoring = {'IBNR':lambda x: x.ibnr_.sum()}
grid = cl.GridSearch(benk, param_grid, scoring=scoring)
# Perform Grid Search
grid.fit(medmal_paid, sample_weight=medmal_prem)

# Plot data
grid.results_.pivot(index='n_iters', columns='apriori', values='IBNR').plot(
    title='Benktander convergence to Chainladder', grid=True).set(ylabel='IBNR')
Пример #14
0
we can see that the "Inverse Power" curve fit doesn't converge to its asymptotic
value.

"""
import chainladder as cl

tri = cl.load_sample('clrd').groupby('LOB').sum().loc['medmal', 'CumPaidLoss']


# Create a fuction to grab the scalar tail value.
def scoring(model):
    """ Scoring functions must return a scalar """
    return model.tail_.iloc[0, 0]


# Create a grid of scenarios
param_grid = dict(extrap_periods=list(range(1, 100, 6)),
                  curve=['inverse_power', 'exponential'])

# Fit Grid
model = cl.GridSearch(cl.TailCurve(), param_grid=param_grid,
                      scoring=scoring).fit(tri)

# Plot results
model.results_.pivot(
    columns='curve', index='extrap_periods', values='score').plot(
        grid=True,
        ylim=(1, None),
        title='Curve Fit Sensitivity to Extrapolation Period').set(
            ylabel='Tail Factor')
Пример #15
0
"""
======================================
Tail Curve Fit Comparison
======================================

This example demonstrates how the ``inverse_power`` curve generally produces more
conservative tail factors than the ``exponential`` fit.
"""
import chainladder as cl
import pandas as pd

clrd = cl.load_sample('clrd').groupby('LOB').sum()['CumPaidLoss']
cdf_ip = cl.TailCurve(curve='inverse_power').fit(clrd)
cdf_xp = cl.TailCurve(curve='exponential').fit(clrd)

pd.concat(
    (cdf_ip.tail_.rename("Inverse Power"), cdf_xp.tail_.rename("Exponential")),
    axis=1).plot(kind='bar', grid=True,
                 title='Curve Fit Comparison').set(xlabel='Industry',
                                                   ylabel='Tail Factor')