Ejemplo n.º 1
0
def test_voting_ultimate():
    clrd = cl.load_sample("clrd")[["CumPaidLoss", "EarnedPremDIR"]]
    clrd = clrd[clrd["LOB"] == "wkcomp"]

    bcl_ult = cl.Chainladder().fit(clrd["CumPaidLoss"].sum(), ).ultimate_
    bf_ult = cl.BornhuetterFerguson().fit(
        clrd["CumPaidLoss"].sum(),
        sample_weight=clrd["EarnedPremDIR"].sum().latest_diagonal).ultimate_
    cc_ult = cl.CapeCod().fit(
        clrd["CumPaidLoss"].sum(),
        sample_weight=clrd["EarnedPremDIR"].sum().latest_diagonal).ultimate_

    bcl = cl.Chainladder()
    bf = cl.BornhuetterFerguson()
    cc = cl.CapeCod()

    estimators = [('bcl', bcl), ('bf', bf), ('cc', cc)]
    weights = np.array([[0.25, 0.25, 0.5]] * 4 + [[0, 0.5, 0.5]] * 3 +
                       [[0, 0, 1]] * 3)

    vot_ult = cl.VotingChainladder(estimators=estimators, weights=weights).fit(
        clrd["CumPaidLoss"].sum(),
        sample_weight=clrd["EarnedPremDIR"].sum().latest_diagonal,
    ).ultimate_

    weights = weights[..., np.newaxis]

    assert abs((bcl_ult * weights[..., 0, :] + bf_ult * weights[..., 1, :] +
                cc_ult * weights[..., 2, :]).sum() - vot_ult.sum()) < 1
Ejemplo n.º 2
0
def test_groupby(clrd):
    clrd = clrd[clrd['LOB'] == 'comauto']
    # But only the top 10 get their own CapeCod aprioris. Smaller companies get grouped together
    top_10 = clrd['EarnedPremDIR'].groupby('GRNAME').sum().latest_diagonal
    top_10 = top_10.loc[..., '1997', :].to_frame().nlargest(10)
    cc_groupby = clrd.index['GRNAME'].map(
        lambda x: x if x in top_10.index else 'Remainder')
    idx = clrd.index
    idx['Top 10'] = cc_groupby
    clrd.index = idx

    # All companies share the same development factors regardless of size
    X = cl.Development().fit(clrd['CumPaidLoss'].sum()).transform(
        clrd['CumPaidLoss'])
    sample_weight = clrd['EarnedPremDIR'].latest_diagonal
    a = cl.CapeCod(groupby='Top 10', decay=0.98,
                   trend=0.02).fit(X,
                                   sample_weight=sample_weight).ibnr_.groupby(
                                       'Top 10').sum().sort_index()
    b = cl.CapeCod(decay=0.98,
                   trend=0.02).fit(X.groupby('Top 10').sum(),
                                   sample_weight=sample_weight.groupby(
                                       'Top 10').sum()).ibnr_.sort_index()
    xp = a.get_array_module()
    b = b.set_backend(a.array_backend)
    xp.allclose(xp.nan_to_num(a.values), xp.nan_to_num(b.values), atol=1e-5)
Ejemplo n.º 3
0
def test_trend1():
    tri = cl.load_sample('clrd')[['CumPaidLoss', 'EarnedPremDIR']].sum()
    assert (cl.CapeCod(.05).fit(
        tri['CumPaidLoss'],
        sample_weight=tri['EarnedPremDIR'].latest_diagonal).ibnr_ ==
            cl.CapeCod().fit(
                cl.Trend(.05).fit_transform(tri['CumPaidLoss']),
                sample_weight=tri['EarnedPremDIR'].latest_diagonal).ibnr_)
Ejemplo n.º 4
0
def test_weight_broadcasting():
    clrd = cl.load_sample("clrd")[["CumPaidLoss", "EarnedPremDIR"]]
    clrd = clrd[clrd["LOB"] == "wkcomp"]

    bcl = cl.Chainladder()
    bf = cl.BornhuetterFerguson()
    cc = cl.CapeCod()

    estimators = [('bcl', bcl), ('bf', bf), ('cc', cc)]
    min_dim_weights = np.array([[1, 2, 3]] * 4 + [[0, 0.5, 0.5]] * 3 +
                               [[0, 0, 1]] * 3)
    mid_dim_weights = np.array(
        [[[1, 2, 3]] * 4 + [[0, 0.5, 0.5]] * 3 + [[0, 0, 1]] * 3] * 1)
    max_dim_weights = np.array(
        [[[[1, 2, 3]] * 4 + [[0, 0.5, 0.5]] * 3 + [[0, 0, 1]] * 3] * 1] * 132)

    min_dim_ult = cl.VotingChainladder(
        estimators=estimators, weights=min_dim_weights).fit(
            clrd['CumPaidLoss'],
            sample_weight=clrd["EarnedPremDIR"].latest_diagonal,
        ).ultimate_.sum()
    mid_dim_ult = cl.VotingChainladder(
        estimators=estimators, weights=mid_dim_weights).fit(
            clrd['CumPaidLoss'],
            sample_weight=clrd["EarnedPremDIR"].latest_diagonal,
        ).ultimate_.sum()
    max_dim_ult = cl.VotingChainladder(
        estimators=estimators, weights=max_dim_weights).fit(
            clrd['CumPaidLoss'],
            sample_weight=clrd["EarnedPremDIR"].latest_diagonal,
        ).ultimate_.sum()
    assert (abs(min_dim_ult - mid_dim_ult - max_dim_ult) < 1)
Ejemplo n.º 5
0
def test_voting_ultimate(triangle_data, estimators, weights):
    bcl_ult = cl.Chainladder().fit(
        triangle_data["CumPaidLoss"].sum(), ).ultimate_
    bf_ult = cl.BornhuetterFerguson().fit(
        triangle_data["CumPaidLoss"].sum(),
        sample_weight=triangle_data["EarnedPremDIR"].sum(
        ).latest_diagonal).ultimate_
    cc_ult = cl.CapeCod().fit(triangle_data["CumPaidLoss"].sum(),
                              sample_weight=triangle_data["EarnedPremDIR"].sum(
                              ).latest_diagonal).ultimate_

    vot_ult = cl.VotingChainladder(
        estimators=estimators, weights=weights,
        default_weighting=(1, 2, 3)).fit(
            triangle_data["CumPaidLoss"].sum(),
            sample_weight=triangle_data["EarnedPremDIR"].sum().latest_diagonal,
        ).ultimate_

    direct_weight = np.array([[1, 2, 3]] * 4 + [[0, 0.5, 0.5]] * 3 +
                             [[0, 0, 1]] * 3)
    direct_weight = direct_weight[..., np.newaxis]

    assert abs((
        (bcl_ult * direct_weight[..., 0, :] + bf_ult *
         direct_weight[..., 1, :] + cc_ult * direct_weight[..., 2, :]) /
        direct_weight.sum(axis=-2)).sum() - vot_ult.sum()) < 1
Ejemplo n.º 6
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()
Ejemplo n.º 7
0
def estimators():
    bcl = cl.Chainladder()
    bf = cl.BornhuetterFerguson()
    cc = cl.CapeCod()

    estimators = [('bcl', bcl), ('bf', bf), ('cc', cc)]

    return estimators
Ejemplo n.º 8
0
def test_struhuss():
    X = cl.load_sample("cc_sample")["loss"]
    X = cl.TailConstant(tail=1 / 0.85).fit_transform(
        cl.Development().fit_transform(X))
    sample_weight = cl.load_sample("cc_sample")["exposure"].latest_diagonal
    ibnr = int(
        cl.CapeCod(trend=0.07,
                   decay=0.75).fit(X, sample_weight=sample_weight).ibnr_.sum())
    assert ibnr == 17052
Ejemplo n.º 9
0
def test_misaligned_index2(clrd):
    clrd = clrd['CumPaidLoss']
    w = cl.load_sample('clrd')['EarnedPremDIR'].latest_diagonal
    bcl = cl.Chainladder().fit(
        cl.Development(groupby=['LOB']).fit_transform(clrd))
    bbk = cl.Benktander().fit(
        cl.Development(groupby=['LOB']).fit_transform(clrd), sample_weight=w)
    bcc = cl.CapeCod().fit(cl.Development(groupby=['LOB']).fit_transform(clrd),
                           sample_weight=w)

    a = bcl.ultimate_.iloc[:10].sum().sum()
    b = bcl.predict(clrd.iloc[:10]).ultimate_.sum().sum()
    assert abs(a - b) < 1e-5
    a = bbk.ultimate_.iloc[:10].sum().sum()
    b = bbk.predict(clrd.iloc[:10],
                    sample_weight=w.iloc[:10]).ultimate_.sum().sum()
    assert abs(a - b) < 1e-5
    a = bcc.ultimate_.iloc[:10].sum().sum()
    b = bcc.predict(clrd.iloc[:10],
                    sample_weight=w.iloc[:10]).ultimate_.sum().sum()
    assert abs(a - b) < 1e-5

    a = bcl.ultimate_.iloc[150:153].sum().sum()
    b = bcl.predict(clrd.iloc[150:153]).ultimate_.sum().sum()
    assert abs(a - b) < 1e-5
    a = bbk.ultimate_.iloc[150:153].sum().sum()
    b = bbk.predict(clrd.iloc[150:153],
                    sample_weight=w.iloc[150:153]).ultimate_.sum().sum()
    assert abs(a - b) < 1e-5
    a = bcc.ultimate_.iloc[150:153].sum().sum()
    b = bcc.predict(clrd.iloc[150:153],
                    sample_weight=w.iloc[150:153]).ultimate_.sum().sum()
    assert abs(a - b) < 1e-5

    a = bcl.ultimate_.iloc[150:152].sum().sum()
    b = bcl.predict(clrd.iloc[150:152]).ultimate_.sum().sum()
    assert abs(a - b) < 1e-5
    a = bbk.ultimate_.iloc[150:152].sum().sum()
    b = bbk.predict(clrd.iloc[150:152],
                    sample_weight=w.iloc[150:152]).ultimate_.sum().sum()
    assert abs(a - b) < 1e-5
    a = bcc.ultimate_.iloc[150:152].sum().sum()
    b = bcc.predict(clrd.iloc[150:152],
                    sample_weight=w.iloc[150:152]).ultimate_.sum().sum()
    assert abs(a - b) < 1e-5

    a = bcl.ultimate_.iloc[150].sum().sum()
    b = bcl.predict(clrd.iloc[150]).ultimate_.sum().sum()
    assert abs(a - b) < 1e-5
    a = bbk.ultimate_.iloc[150].sum().sum()
    b = bbk.predict(clrd.iloc[150],
                    sample_weight=w.iloc[150]).ultimate_.sum().sum()
    assert abs(a - b) < 1e-5
    a = bcc.ultimate_.iloc[150].sum().sum()
    b = bcc.predict(clrd.iloc[150],
                    sample_weight=w.iloc[150]).ultimate_.sum().sum()
    assert abs(a - b) < 1e-5
Ejemplo n.º 10
0
def test_voting_predict():
    bcl = cl.Chainladder()
    bf = cl.BornhuetterFerguson()
    cc = cl.CapeCod()

    estimators = [('bcl', bcl), ('bf', bf), ('cc', cc)]
    weights = np.array([[1, 2, 3]] * 3 + [[0, 0.5, 0.5]] * 3 + [[0, 0, 1]] * 3)

    vot = cl.VotingChainladder(estimators=estimators, weights=weights).fit(
        raa_1989,
        sample_weight=apriori_1989,
    )
    vot.predict(raa_1990, sample_weight=apriori_1990)
Ejemplo n.º 11
0
def test_different_backends():
    clrd = cl.load_sample("clrd")[["CumPaidLoss", "EarnedPremDIR"]]
    clrd = clrd[clrd["LOB"] == "wkcomp"]

    bcl = cl.Chainladder()
    bf = cl.BornhuetterFerguson()
    cc = cl.CapeCod()

    estimators = [('bcl', bcl), ('bf', bf), ('cc', cc)]
    weights = np.array([[1, 2, 3]] * 4 + [[0, 0.5, 0.5]] * 3 + [[0, 0, 1]] * 3)

    model = cl.VotingChainladder(estimators=estimators, weights=weights).fit(
        clrd["CumPaidLoss"].sum().set_backend("numpy"),
        sample_weight=clrd["EarnedPremDIR"].sum().latest_diagonal.set_backend(
            "numpy"),
    )
    assert (abs(
        (model.predict(clrd["CumPaidLoss"].sum().set_backend("sparse"),
                       sample_weight=clrd["EarnedPremDIR"].sum().
                       latest_diagonal.set_backend("sparse")).ultimate_.sum() -
         model.ultimate_.sum())) < 1)
Ejemplo n.º 12
0
# Loss on-leveling factors
tort_reform = pd.DataFrame({
    'date': ['1/1/2006', '1/1/2007'],
    'rate_change': [-0.1067, -.25]
})

# In addition to development, include onlevel estimator in pipeline for loss
pipe = cl.Pipeline(steps=[('olf',
                           cl.ParallelogramOLF(tort_reform,
                                               change_col='rate_change',
                                               date_col='date',
                                               vertical_line=True)
                           ), ('dev', cl.Development(
                               n_periods=2)), ('model',
                                               cl.CapeCod(trend=0.034))])

# Define X
X = cl.load_sample('xyz')['Incurred']

# Separately apply on-level factors for premium
sample_weight = cl.ParallelogramOLF(rate_history,
                                    change_col='rate_change',
                                    date_col='date',
                                    vertical_line=True).fit_transform(
                                        xyz['Premium'].latest_diagonal)

#  Fit Cod Estimator
pipe.fit(X, sample_weight=sample_weight).named_steps.model.ultimate_

# Create a Cape Cod pipeline without onleveling
Ejemplo n.º 13
0
def get_apriori(decay, trend):
    """ Function to grab apriori array from cape cod method """
    cc = cl.CapeCod(decay=decay, trend=trend)
    cc.fit(ppauto_loss, sample_weight=ppauto_prem)
    return cc.detrended_apriori_.to_frame()
def test_cc_predict():
    cc = cl.CapeCod().fit(raa_1989, sample_weight=apriori_1989)
    cc.predict(raa, sample_weight=apriori)
==========================

This example demonstrates how you can can use the Voting Chainladder method.
"""
import numpy as np
import pandas as pd
import chainladder as cl

# Load the data
raa = cl.load_sample('raa')
cl_ult = cl.Chainladder().fit(raa).ultimate_  # Chainladder Ultimate
apriori = cl_ult * 0 + (float(cl_ult.sum()) / 10)  # Mean Chainladder Ultimate

# Load estimators to vote between
bcl = cl.Chainladder()
cc = cl.CapeCod()
estimators = [('bcl', bcl), ('cc', cc)]

# Fit VotingChainladder using CC after 1987 and a blend of BCL and CC otherwise
vot = cl.VotingChainladder(
    estimators=estimators,
    weights=lambda origin: (0, 1) if origin.year > 1987 else (0.5, 0.5)
    )
vot.fit(raa, sample_weight=apriori)

# Plotting
bcl_ibnr = bcl.fit(raa).ibnr_.to_frame()
cc_ibnr = cc.fit(raa, sample_weight=apriori).ibnr_.to_frame()
vot_ibnr = vot.ibnr_.to_frame()

plot_ibnr = pd.concat([bcl_ibnr, vot_ibnr, cc_ibnr], axis=1)