Triangle Visualization#

Chainladder’s Styler class enables visual customization of triangles when displayed in a Jupyter notebook. Any styling options that can be applied to a Pandas DataFrame can also be applied to a Chainladder Triangle. In addition, the Styler extends its Pandas counterpart with methods designed for actuaries.

Note

The Styler only works on single triangles.

Highlighting the lower triangle#

The lower triangle contains cells that extend beyond the latest diagonal. This area can be highlited with Triangle.style.highlight_lower_triangle().

import chainladder as cl

raa = cl.load_sample("raa")

raa.style.highlight_lower_triangle(color="blue")
  12 24 36 48 60 72 84 96 108 120
1981 5,012 8,269 10,907 11,805 13,539 16,181 18,009 18,608 18,662 18,834
1982 106 4,285 5,396 10,666 13,782 15,599 15,496 16,169 16,704
1983 3,410 8,992 13,873 16,141 18,735 22,214 22,863 23,466
1984 5,655 11,555 15,766 21,266 23,425 26,083 27,067
1985 1,092 9,565 15,836 22,169 25,955 26,180
1986 1,513 6,445 11,702 12,935 15,852
1987 557 4,020 10,946 12,314
1988 1,351 6,947 13,112
1989 3,133 5,395
1990 2,063

You may find that the blue contrasts too sharply against the white background of this website. You can change the color to a lighter shade of blue, and the text to white to improve readability.

full = cl.Chainladder().fit(raa).full_triangle_
full.style.highlight_lower_triangle(
    color="#2F61AD",
    text_color="#FFFFFF",
)
  12 24 36 48 60 72 84 96 108 120 132 9999
1981 5,012 8,269 10,907 11,805 13,539 16,181 18,009 18,608 18,662 18,834 18,834 18,834
1982 106 4,285 5,396 10,666 13,782 15,599 15,496 16,169 16,704 16,858 16,858 16,858
1983 3,410 8,992 13,873 16,141 18,735 22,214 22,863 23,466 23,863 24,083 24,083 24,083
1984 5,655 11,555 15,766 21,266 23,425 26,083 27,067 27,967 28,441 28,703 28,703 28,703
1985 1,092 9,565 15,836 22,169 25,955 26,180 27,278 28,185 28,663 28,927 28,927 28,927
1986 1,513 6,445 11,702 12,935 15,852 17,649 18,389 19,001 19,323 19,501 19,501 19,501
1987 557 4,020 10,946 12,314 14,428 16,064 16,738 17,294 17,587 17,749 17,749 17,749
1988 1,351 6,947 13,112 16,664 19,525 21,738 22,650 23,403 23,800 24,019 24,019 24,019
1989 3,133 5,395 8,759 11,132 13,043 14,521 15,130 15,634 15,898 16,045 16,045 16,045
1990 2,063 6,188 10,046 12,767 14,959 16,655 17,353 17,931 18,234 18,402 18,402 18,402

Highlighting diagonals#

Diagonals represent cells sharing the same valuation date. The latest diagonal can be highlighted with Triangle.style.highlight_diagonal(). You can also specify a particular valuation date, or chain diagonal and lower triangle styling together.

# Highlight the latest diagonal and the lower triangle together
raa.style.highlight_diagonal(color="#FFE599").highlight_lower_triangle(color="#DDEBF7")
  12 24 36 48 60 72 84 96 108 120
1981 5,012 8,269 10,907 11,805 13,539 16,181 18,009 18,608 18,662 18,834
1982 106 4,285 5,396 10,666 13,782 15,599 15,496 16,169 16,704
1983 3,410 8,992 13,873 16,141 18,735 22,214 22,863 23,466
1984 5,655 11,555 15,766 21,266 23,425 26,083 27,067
1985 1,092 9,565 15,836 22,169 25,955 26,180
1986 1,513 6,445 11,702 12,935 15,852
1987 557 4,020 10,946 12,314
1988 1,351 6,947 13,112
1989 3,133 5,395
1990 2,063

Applying styles from a Triangle#

For custom styling patterns, Triangle.style.apply_from_triangle() allows you to style cells based on a mask Triangle. Cells where the mask has non-missing (or truthy) values are highlighted.

For example, you can highlight cells by slicing a Triangle:

# Highlight the latest diagonal via valuation slicing
raa.style.apply_from_triangle(
    raa[raa.valuation == raa.valuation_date],
    color="#FFE599",
)
  12 24 36 48 60 72 84 96 108 120
1981 5,012 8,269 10,907 11,805 13,539 16,181 18,009 18,608 18,662 18,834
1982 106 4,285 5,396 10,666 13,782 15,599 15,496 16,169 16,704
1983 3,410 8,992 13,873 16,141 18,735 22,214 22,863 23,466
1984 5,655 11,555 15,766 21,266 23,425 26,083 27,067
1985 1,092 9,565 15,836 22,169 25,955 26,180
1986 1,513 6,445 11,702 12,935 15,852
1987 557 4,020 10,946 12,314
1988 1,351 6,947 13,112
1989 3,133 5,395
1990 2,063

Numeric Formatting#

The Styler allows you to control the numeric format of a Triangle’s values. Let’s change the precision of the link ratios to have 3 decimal places.

raa.link_ratio.style.format(
    precision=3,
    na_rep="",
)
  12-24 24-36 36-48 48-60 60-72 72-84 84-96 96-108 108-120
1981 1.650 1.319 1.082 1.147 1.195 1.113 1.033 1.003 1.009
1982 40.425 1.259 1.977 1.292 1.132 0.993 1.043 1.033
1983 2.637 1.543 1.163 1.161 1.186 1.029 1.026
1984 2.043 1.364 1.349 1.102 1.113 1.038
1985 8.759 1.656 1.400 1.171 1.009
1986 4.260 1.816 1.105 1.226
1987 7.217 2.723 1.125
1988 5.142 1.887
1989 1.722

Localization#

Chainladder is used by actuaries all over the world. The Styler can be used to adapt the numeric formatting to specific locales. Let’s try formating genins with the Swiss numbering format, which uses apostrophes as the thousands separator.

genins = cl.load_sample("genins")

genins.style.format(
    precision=0,
    thousands="'",
    na_rep="",
)
  12 24 36 48 60 72 84 96 108 120
2001 357'848 1'124'788 1'735'330 2'218'270 2'745'596 3'319'994 3'466'336 3'606'286 3'833'515 3'901'463
2002 352'118 1'236'139 2'170'033 3'353'322 3'799'067 4'120'063 4'647'867 4'914'039 5'339'085
2003 290'507 1'292'306 2'218'525 3'235'179 3'985'995 4'132'918 4'628'910 4'909'315
2004 310'608 1'418'858 2'195'047 3'757'447 4'029'929 4'381'982 4'588'268
2005 443'160 1'136'350 2'128'333 2'897'821 3'402'672 3'873'311
2006 396'132 1'333'217 2'180'715 2'985'752 3'691'712
2007 440'832 1'288'463 2'419'861 3'483'130
2008 359'480 1'421'128 2'864'498
2009 376'686 1'363'294
2010 344'014

Babel#

You can supply a format using the babel package if you have it installed. Let’s try the Indian numeric format.

from babel.numbers import format_decimal

# The Indian numbering system groups by lakh and crore: 12,34,567.
genins.style.format(
    lambda x: format_decimal(x, locale="en_IN"),
    na_rep="",
)
  12 24 36 48 60 72 84 96 108 120
2001 3,57,848 11,24,788 17,35,330 22,18,270 27,45,596 33,19,994 34,66,336 36,06,286 38,33,515 39,01,463
2002 3,52,118 12,36,139 21,70,033 33,53,322 37,99,067 41,20,063 46,47,867 49,14,039 53,39,085
2003 2,90,507 12,92,306 22,18,525 32,35,179 39,85,995 41,32,918 46,28,910 49,09,315
2004 3,10,608 14,18,858 21,95,047 37,57,447 40,29,929 43,81,982 45,88,268
2005 4,43,160 11,36,350 21,28,333 28,97,821 34,02,672 38,73,311
2006 3,96,132 13,33,217 21,80,715 29,85,752 36,91,712
2007 4,40,832 12,88,463 24,19,861 34,83,130
2008 3,59,480 14,21,128 28,64,498
2009 3,76,686 13,63,294
2010 3,44,014