{ "cells": [ { "cell_type": "markdown", "id": "adf3239d", "metadata": {}, "source": [ "# Business Cycles" ] }, { "cell_type": "markdown", "id": "65dac574", "metadata": {}, "source": [ "## Overview\n", "\n", "In this lecture we review some empirical aspects of business cycles.\n", "\n", "Business cycles are fluctuations in economic activity over time.\n", "\n", "These include expansions (also called booms) and contractions (also called recessions).\n", "\n", "For our study, we will use economic indicators from the [World Bank](https://documents.worldbank.org/en/publication/documents-reports/api) and [FRED](https://fred.stlouisfed.org/).\n", "\n", "In addition to the packages already installed by Anaconda, this lecture requires" ] }, { "cell_type": "code", "execution_count": null, "id": "cbe6e3c8", "metadata": { "hide-output": false }, "outputs": [], "source": [ "!pip install wbgapi\n", "!pip install pandas-datareader" ] }, { "cell_type": "markdown", "id": "d7731375", "metadata": {}, "source": [ "We use the following imports" ] }, { "cell_type": "code", "execution_count": null, "id": "52fbe646", "metadata": { "hide-output": false }, "outputs": [], "source": [ "import matplotlib.pyplot as plt\n", "import pandas as pd\n", "import datetime\n", "import wbgapi as wb\n", "import pandas_datareader.data as web" ] }, { "cell_type": "markdown", "id": "20db73d1", "metadata": {}, "source": [ "Here’s some minor code to help with colors in our plots." ] }, { "cell_type": "code", "execution_count": null, "id": "7dccf89b", "metadata": { "hide-output": false }, "outputs": [], "source": [ "# Set graphical parameters\n", "cycler = plt.cycler(linestyle=['-', '-.', '--', ':'], \n", " color=['#377eb8', '#ff7f00', '#4daf4a', '#ff334f'])\n", "plt.rc('axes', prop_cycle=cycler)" ] }, { "cell_type": "markdown", "id": "332fafec", "metadata": {}, "source": [ "## Data acquisition\n", "\n", "We will use the World Bank’s data API `wbgapi` and `pandas_datareader` to retrieve data.\n", "\n", "We can use `wb.series.info` with the argument `q` to query available data from\n", "the [World Bank](https://www.worldbank.org/en/home).\n", "\n", "For example, let’s retrieve the GDP growth data ID to query GDP growth data." ] }, { "cell_type": "code", "execution_count": null, "id": "47761e71", "metadata": { "hide-output": false }, "outputs": [], "source": [ "wb.series.info(q='GDP growth')" ] }, { "cell_type": "markdown", "id": "bfe8f5ac", "metadata": {}, "source": [ "Now we use this series ID to obtain the data." ] }, { "cell_type": "code", "execution_count": null, "id": "feb0f3d5", "metadata": { "hide-output": false }, "outputs": [], "source": [ "gdp_growth = wb.data.DataFrame('NY.GDP.MKTP.KD.ZG',\n", " ['USA', 'ARG', 'GBR', 'GRC', 'JPN'], \n", " labels=True)\n", "gdp_growth" ] }, { "cell_type": "markdown", "id": "615c76d5", "metadata": {}, "source": [ "We can look at the series’ metadata to learn more about the series (click to expand)." ] }, { "cell_type": "code", "execution_count": null, "id": "14719bf9", "metadata": { "hide-output": false }, "outputs": [], "source": [ "wb.series.metadata.get('NY.GDP.MKTP.KD.ZG')" ] }, { "cell_type": "markdown", "id": "e01dbe32", "metadata": {}, "source": [ "\n", "<a id='gdp-growth'></a>" ] }, { "cell_type": "markdown", "id": "8bec60e6", "metadata": {}, "source": [ "## GDP growth rate\n", "\n", "First we look at GDP growth.\n", "\n", "Let’s source our data from the World Bank and clean it." ] }, { "cell_type": "code", "execution_count": null, "id": "52e3c72d", "metadata": { "hide-output": false }, "outputs": [], "source": [ "# Use the series ID retrieved before\n", "gdp_growth = wb.data.DataFrame('NY.GDP.MKTP.KD.ZG',\n", " ['USA', 'ARG', 'GBR', 'GRC', 'JPN'], \n", " labels=True)\n", "gdp_growth = gdp_growth.set_index('Country')\n", "gdp_growth.columns = gdp_growth.columns.str.replace('YR', '').astype(int)" ] }, { "cell_type": "markdown", "id": "0fb83b09", "metadata": {}, "source": [ "Here’s a first look at the data" ] }, { "cell_type": "code", "execution_count": null, "id": "def8b9fa", "metadata": { "hide-output": false }, "outputs": [], "source": [ "gdp_growth" ] }, { "cell_type": "markdown", "id": "bc696116", "metadata": {}, "source": [ "We write a function to generate plots for individual countries taking into account the recessions." ] }, { "cell_type": "code", "execution_count": null, "id": "1c687934", "metadata": { "hide-output": false }, "outputs": [], "source": [ "def plot_series(data, country, ylabel, \n", " txt_pos, ax, g_params,\n", " b_params, t_params, ylim=15, baseline=0):\n", " \"\"\"\n", " Plots a time series with recessions highlighted. \n", "\n", " Parameters\n", " ----------\n", " data : pd.DataFrame\n", " Data to plot\n", " country : str\n", " Name of the country to plot\n", " ylabel : str\n", " Label of the y-axis\n", " txt_pos : float\n", " Position of the recession labels\n", " y_lim : float\n", " Limit of the y-axis\n", " ax : matplotlib.axes._subplots.AxesSubplot\n", " Axes to plot on\n", " g_params : dict\n", " Parameters for the line\n", " b_params : dict\n", " Parameters for the recession highlights\n", " t_params : dict\n", " Parameters for the recession labels\n", " baseline : float, optional\n", " Dashed baseline on the plot, by default 0\n", " \n", " Returns\n", " -------\n", " ax : matplotlib.axes.Axes\n", " Axes with the plot.\n", " \"\"\"\n", "\n", " ax.plot(data.loc[country], label=country, **g_params)\n", " \n", " # Highlight recessions\n", " ax.axvspan(1973, 1975, **b_params)\n", " ax.axvspan(1990, 1992, **b_params)\n", " ax.axvspan(2007, 2009, **b_params)\n", " ax.axvspan(2019, 2021, **b_params)\n", " if ylim != None:\n", " ax.set_ylim([-ylim, ylim])\n", " else:\n", " ylim = ax.get_ylim()[1]\n", " ax.text(1974, ylim + ylim*txt_pos,\n", " 'Oil Crisis\\n(1974)', **t_params) \n", " ax.text(1991, ylim + ylim*txt_pos,\n", " '1990s recession\\n(1991)', **t_params) \n", " ax.text(2008, ylim + ylim*txt_pos,\n", " 'GFC\\n(2008)', **t_params) \n", " ax.text(2020, ylim + ylim*txt_pos,\n", " 'Covid-19\\n(2020)', **t_params)\n", "\n", " # Add a baseline for reference\n", " if baseline != None:\n", " ax.axhline(y=baseline, \n", " color='black', \n", " linestyle='--')\n", " ax.set_ylabel(ylabel)\n", " ax.legend()\n", " return ax\n", "\n", "# Define graphical parameters \n", "g_params = {'alpha': 0.7}\n", "b_params = {'color':'grey', 'alpha': 0.2}\n", "t_params = {'color':'grey', 'fontsize': 9, \n", " 'va':'center', 'ha':'center'}" ] }, { "cell_type": "markdown", "id": "e40561cc", "metadata": {}, "source": [ "Let’s start with the United States." ] }, { "cell_type": "code", "execution_count": null, "id": "b53eb04a", "metadata": { "hide-output": false }, "outputs": [], "source": [ "fig, ax = plt.subplots()\n", "\n", "country = 'United States'\n", "ylabel = 'GDP growth rate (%)'\n", "plot_series(gdp_growth, country, \n", " ylabel, 0.1, ax, \n", " g_params, b_params, t_params)\n", "plt.show()" ] }, { "cell_type": "markdown", "id": "10aa1e1c", "metadata": {}, "source": [ "GDP growth is positive on average and trending slightly downward over time.\n", "\n", "We also see fluctuations over GDP growth over time, some of which are quite large.\n", "\n", "Let’s look at a few more countries to get a basis for comparison.\n", "\n", "The United Kingdom (UK) has a similar pattern to the US, with a slow decline\n", "in the growth rate and significant fluctuations.\n", "\n", "Notice the very large dip during the Covid-19 pandemic." ] }, { "cell_type": "code", "execution_count": null, "id": "cbe38b30", "metadata": { "hide-output": false }, "outputs": [], "source": [ "fig, ax = plt.subplots()\n", "\n", "country = 'United Kingdom'\n", "plot_series(gdp_growth, country, \n", " ylabel, 0.1, ax, \n", " g_params, b_params, t_params)\n", "plt.show()" ] }, { "cell_type": "markdown", "id": "59cf7308", "metadata": {}, "source": [ "Now let’s consider Japan, which experienced rapid growth in the 1960s and\n", "1970s, followed by slowed expansion in the past two decades.\n", "\n", "Major dips in the growth rate coincided with the Oil Crisis of the 1970s, the\n", "Global Financial Crisis (GFC) and the Covid-19 pandemic." ] }, { "cell_type": "code", "execution_count": null, "id": "b51491b5", "metadata": { "hide-output": false }, "outputs": [], "source": [ "fig, ax = plt.subplots()\n", "\n", "country = 'Japan'\n", "plot_series(gdp_growth, country, \n", " ylabel, 0.1, ax, \n", " g_params, b_params, t_params)\n", "plt.show()" ] }, { "cell_type": "markdown", "id": "67faa5cb", "metadata": {}, "source": [ "Now let’s study Greece." ] }, { "cell_type": "code", "execution_count": null, "id": "eec3a250", "metadata": { "hide-output": false }, "outputs": [], "source": [ "fig, ax = plt.subplots()\n", "\n", "country = 'Greece'\n", "plot_series(gdp_growth, country, \n", " ylabel, 0.1, ax, \n", " g_params, b_params, t_params)\n", "plt.show()" ] }, { "cell_type": "markdown", "id": "d4fb05d0", "metadata": {}, "source": [ "Greece experienced a very large drop in GDP growth around 2010-2011, during the peak\n", "of the Greek debt crisis.\n", "\n", "Next let’s consider Argentina." ] }, { "cell_type": "code", "execution_count": null, "id": "2631950c", "metadata": { "hide-output": false }, "outputs": [], "source": [ "fig, ax = plt.subplots()\n", "\n", "country = 'Argentina'\n", "plot_series(gdp_growth, country, \n", " ylabel, 0.1, ax, \n", " g_params, b_params, t_params)\n", "plt.show()" ] }, { "cell_type": "markdown", "id": "4386ba6e", "metadata": {}, "source": [ "Notice that Argentina has experienced far more volatile cycles than\n", "the economies examined above.\n", "\n", "At the same time, Argentina’s growth rate did not fall during the two developed\n", "economy recessions in the 1970s and 1990s." ] }, { "cell_type": "markdown", "id": "1f5a4701", "metadata": {}, "source": [ "## Unemployment\n", "\n", "Another important measure of business cycles is the unemployment rate.\n", "\n", "We study unemployment using rate data from FRED spanning from [1929-1942](https://fred.stlouisfed.org/series/M0892AUSM156SNBR) to [1948-2022](https://fred.stlouisfed.org/series/UNRATE), combined unemployment rate data over 1942-1948 estimated by the [Census Bureau](https://www.census.gov/library/publications/1975/compendia/hist_stats_colonial-1970.html)." ] }, { "cell_type": "code", "execution_count": null, "id": "99a0905c", "metadata": { "hide-output": false }, "outputs": [], "source": [ "start_date = datetime.datetime(1929, 1, 1)\n", "end_date = datetime.datetime(1942, 6, 1)\n", "\n", "unrate_history = web.DataReader('M0892AUSM156SNBR', \n", " 'fred', start_date,end_date)\n", "unrate_history.rename(columns={'M0892AUSM156SNBR': 'UNRATE'}, \n", " inplace=True)\n", "\n", "start_date = datetime.datetime(1948, 1, 1)\n", "end_date = datetime.datetime(2022, 12, 31)\n", "\n", "unrate = web.DataReader('UNRATE', 'fred', \n", " start_date, end_date)" ] }, { "cell_type": "markdown", "id": "577629cc", "metadata": {}, "source": [ "Let’s plot the unemployment rate in the US from 1929 to 2022 with recessions\n", "defined by the NBER." ] }, { "cell_type": "code", "execution_count": null, "id": "60eb29c8", "metadata": { "hide-output": false }, "outputs": [], "source": [ "# We use the census bureau's estimate for the unemployment rate \n", "# between 1942 and 1948\n", "years = [datetime.datetime(year, 6, 1) for year in range(1942, 1948)]\n", "unrate_census = [4.7, 1.9, 1.2, 1.9, 3.9, 3.9]\n", "\n", "unrate_census = {'DATE': years, 'UNRATE': unrate_census}\n", "unrate_census = pd.DataFrame(unrate_census)\n", "unrate_census.set_index('DATE', inplace=True)\n", "\n", "# Obtain the NBER-defined recession periods\n", "start_date = datetime.datetime(1929, 1, 1)\n", "end_date = datetime.datetime(2022, 12, 31)\n", "\n", "nber = web.DataReader('USREC', 'fred', start_date, end_date)\n", "\n", "fig, ax = plt.subplots()\n", "\n", "ax.plot(unrate_history, **g_params, \n", " color='#377eb8', \n", " linestyle='-', linewidth=2)\n", "ax.plot(unrate_census, **g_params, \n", " color='black', linestyle='--', \n", " label='Census estimates', linewidth=2)\n", "ax.plot(unrate, **g_params, color='#377eb8', \n", " linestyle='-', linewidth=2)\n", "\n", "# Draw gray boxes according to NBER recession indicators\n", "ax.fill_between(nber.index, 0, 1,\n", " where=nber['USREC']==1, \n", " color='grey', edgecolor='none',\n", " alpha=0.3, \n", " transform=ax.get_xaxis_transform(), \n", " label='NBER recession indicators')\n", "ax.set_ylim([0, ax.get_ylim()[1]])\n", "ax.legend(loc='upper center', \n", " bbox_to_anchor=(0.5, 1.1),\n", " ncol=3, fancybox=True, shadow=True)\n", "ax.set_ylabel('unemployment rate (%)')\n", "\n", "plt.show()" ] }, { "cell_type": "markdown", "id": "78fe35bd", "metadata": {}, "source": [ "The plot shows that\n", "\n", "- expansions and contractions of the labor market have been highly correlated\n", " with recessions. \n", "- cycles are, in general, asymmetric: sharp rises in unemployment are followed\n", " by slow recoveries. \n", "\n", "\n", "It also shows us how unique labor market conditions were in the US during the\n", "post-pandemic recovery.\n", "\n", "The labor market recovered at an unprecedented rate after the shock in 2020-2021.\n", "\n", "\n", "<a id='synchronization'></a>" ] }, { "cell_type": "markdown", "id": "aff2d50d", "metadata": {}, "source": [ "## Synchronization\n", "\n", "In our [previous discussion](#gdp-growth), we found that developed economies have had\n", "relatively synchronized periods of recession.\n", "\n", "At the same time, this synchronization did not appear in Argentina until the 2000s.\n", "\n", "Let’s examine this trend further.\n", "\n", "With slight modifications, we can use our previous function to draw a plot\n", "that includes multiple countries." ] }, { "cell_type": "code", "execution_count": null, "id": "2e8b2449", "metadata": { "hide-output": false }, "outputs": [], "source": [ "\n", "def plot_comparison(data, countries, \n", " ylabel, txt_pos, y_lim, ax, \n", " g_params, b_params, t_params, \n", " baseline=0):\n", " \"\"\"\n", " Plot multiple series on the same graph\n", "\n", " Parameters\n", " ----------\n", " data : pd.DataFrame\n", " Data to plot\n", " countries : list\n", " List of countries to plot\n", " ylabel : str\n", " Label of the y-axis\n", " txt_pos : float\n", " Position of the recession labels\n", " y_lim : float\n", " Limit of the y-axis\n", " ax : matplotlib.axes._subplots.AxesSubplot\n", " Axes to plot on\n", " g_params : dict\n", " Parameters for the lines\n", " b_params : dict\n", " Parameters for the recession highlights\n", " t_params : dict\n", " Parameters for the recession labels\n", " baseline : float, optional\n", " Dashed baseline on the plot, by default 0\n", " \n", " Returns\n", " -------\n", " ax : matplotlib.axes.Axes\n", " Axes with the plot.\n", " \"\"\"\n", " \n", " # Allow the function to go through more than one series\n", " for country in countries:\n", " ax.plot(data.loc[country], label=country, **g_params)\n", " \n", " # Highlight recessions\n", " ax.axvspan(1973, 1975, **b_params)\n", " ax.axvspan(1990, 1992, **b_params)\n", " ax.axvspan(2007, 2009, **b_params)\n", " ax.axvspan(2019, 2021, **b_params)\n", " if y_lim != None:\n", " ax.set_ylim([-y_lim, y_lim])\n", " ylim = ax.get_ylim()[1]\n", " ax.text(1974, ylim + ylim*txt_pos, \n", " 'Oil Crisis\\n(1974)', **t_params) \n", " ax.text(1991, ylim + ylim*txt_pos, \n", " '1990s recession\\n(1991)', **t_params) \n", " ax.text(2008, ylim + ylim*txt_pos, \n", " 'GFC\\n(2008)', **t_params) \n", " ax.text(2020, ylim + ylim*txt_pos, \n", " 'Covid-19\\n(2020)', **t_params) \n", " if baseline != None:\n", " ax.hlines(y=baseline, xmin=ax.get_xlim()[0], \n", " xmax=ax.get_xlim()[1], color='black', \n", " linestyle='--')\n", " ax.set_ylabel(ylabel)\n", " ax.legend()\n", " return ax\n", "\n", "# Define graphical parameters \n", "g_params = {'alpha': 0.7}\n", "b_params = {'color':'grey', 'alpha': 0.2}\n", "t_params = {'color':'grey', 'fontsize': 9, \n", " 'va':'center', 'ha':'center'}" ] }, { "cell_type": "markdown", "id": "db9d819e", "metadata": {}, "source": [ "Here we compare the GDP growth rate of developed economies and developing economies." ] }, { "cell_type": "code", "execution_count": null, "id": "306a6507", "metadata": { "hide-output": false }, "outputs": [], "source": [ "# Obtain GDP growth rate for a list of countries\n", "gdp_growth = wb.data.DataFrame('NY.GDP.MKTP.KD.ZG',\n", " ['CHN', 'USA', 'DEU', 'BRA', 'ARG', 'GBR', 'JPN', 'MEX'], \n", " labels=True)\n", "gdp_growth = gdp_growth.set_index('Country')\n", "gdp_growth.columns = gdp_growth.columns.str.replace('YR', '').astype(int)" ] }, { "cell_type": "markdown", "id": "76749ca3", "metadata": {}, "source": [ "We use the United Kingdom, United States, Germany, and Japan as examples of developed economies." ] }, { "cell_type": "code", "execution_count": null, "id": "33bf1904", "metadata": { "hide-output": false }, "outputs": [], "source": [ "fig, ax = plt.subplots()\n", "countries = ['United Kingdom', 'United States', 'Germany', 'Japan']\n", "ylabel = 'GDP growth rate (%)'\n", "plot_comparison(gdp_growth.loc[countries, 1962:], \n", " countries, ylabel,\n", " 0.1, 20, ax, \n", " g_params, b_params, t_params)\n", "plt.show()" ] }, { "cell_type": "markdown", "id": "08b6da49", "metadata": {}, "source": [ "We choose Brazil, China, Argentina, and Mexico as representative developing economies." ] }, { "cell_type": "code", "execution_count": null, "id": "ac3907c8", "metadata": { "hide-output": false }, "outputs": [], "source": [ "fig, ax = plt.subplots()\n", "countries = ['Brazil', 'China', 'Argentina', 'Mexico']\n", "plot_comparison(gdp_growth.loc[countries, 1962:], \n", " countries, ylabel, \n", " 0.1, 20, ax, \n", " g_params, b_params, t_params)\n", "plt.show()" ] }, { "cell_type": "markdown", "id": "c38f3039", "metadata": {}, "source": [ "The comparison of GDP growth rates above suggests that\n", "business cycles are becoming more synchronized in 21st-century recessions.\n", "\n", "However, emerging and less developed economies often experience more volatile\n", "changes throughout the economic cycles.\n", "\n", "Despite the synchronization in GDP growth, the experience of individual countries during\n", "the recession often differs.\n", "\n", "We use the unemployment rate and the recovery of labor market conditions\n", "as another example.\n", "\n", "Here we compare the unemployment rate of the United States,\n", "the United Kingdom, Japan, and France." ] }, { "cell_type": "code", "execution_count": null, "id": "b8bcf964", "metadata": { "hide-output": false }, "outputs": [], "source": [ "unempl_rate = wb.data.DataFrame('SL.UEM.TOTL.NE.ZS',\n", " ['USA', 'FRA', 'GBR', 'JPN'], labels=True)\n", "unempl_rate = unempl_rate.set_index('Country')\n", "unempl_rate.columns = unempl_rate.columns.str.replace('YR', '').astype(int)\n", "\n", "fig, ax = plt.subplots()\n", "\n", "countries = ['United Kingdom', 'United States', 'Japan', 'France']\n", "ylabel = 'unemployment rate (national estimate) (%)'\n", "plot_comparison(unempl_rate, countries, \n", " ylabel, 0.05, None, ax, g_params, \n", " b_params, t_params, baseline=None)\n", "plt.show()" ] }, { "cell_type": "markdown", "id": "aa5a15b0", "metadata": {}, "source": [ "We see that France, with its strong labor unions, typically experiences\n", "relatively slow labor market recoveries after negative shocks.\n", "\n", "We also notice that Japan has a history of very low and stable unemployment rates." ] }, { "cell_type": "markdown", "id": "15492b77", "metadata": {}, "source": [ "## Leading indicators and correlated factors\n", "\n", "Examining leading indicators and correlated factors helps policymakers to\n", "understand the causes and results of business cycles.\n", "\n", "We will discuss potential leading indicators and correlated factors from three\n", "perspectives: consumption, production, and credit level." ] }, { "cell_type": "markdown", "id": "a250813f", "metadata": {}, "source": [ "### Consumption\n", "\n", "Consumption depends on consumers’ confidence towards their\n", "income and the overall performance of the economy in the future.\n", "\n", "One widely cited indicator for consumer confidence is the [consumer sentiment index](https://fred.stlouisfed.org/series/UMCSENT) published by the University\n", "of Michigan.\n", "\n", "Here we plot the University of Michigan Consumer Sentiment Index and\n", "year-on-year\n", "[core consumer price index](https://fred.stlouisfed.org/series/CPILFESL)\n", "(CPI) change from 1978-2022 in the US." ] }, { "cell_type": "code", "execution_count": null, "id": "010e1ab1", "metadata": { "hide-output": false }, "outputs": [], "source": [ "start_date = datetime.datetime(1978, 1, 1)\n", "end_date = datetime.datetime(2022, 12, 31)\n", "\n", "# Limit the plot to a specific range\n", "start_date_graph = datetime.datetime(1977, 1, 1)\n", "end_date_graph = datetime.datetime(2023, 12, 31)\n", "\n", "nber = web.DataReader('USREC', 'fred', start_date, end_date)\n", "consumer_confidence = web.DataReader('UMCSENT', 'fred', \n", " start_date, end_date)\n", "\n", "fig, ax = plt.subplots()\n", "ax.plot(consumer_confidence, **g_params, \n", " color='#377eb8', linestyle='-', \n", " linewidth=2)\n", "ax.fill_between(nber.index, 0, 1, \n", " where=nber['USREC']==1, \n", " color='grey', edgecolor='none',\n", " alpha=0.3, \n", " transform=ax.get_xaxis_transform(), \n", " label='NBER recession indicators')\n", "ax.set_ylim([0, ax.get_ylim()[1]])\n", "ax.set_ylabel('consumer sentiment index')\n", "\n", "# Plot CPI on another y-axis\n", "ax_t = ax.twinx()\n", "inflation = web.DataReader('CPILFESL', 'fred', \n", " start_date, end_date).pct_change(12)*100\n", "\n", "# Add CPI on the legend without drawing the line again\n", "ax_t.plot(2020, 0, **g_params, linestyle='-', \n", " linewidth=2, label='consumer sentiment index')\n", "ax_t.plot(inflation, **g_params, \n", " color='#ff7f00', linestyle='--', \n", " linewidth=2, label='CPI YoY change (%)')\n", "\n", "ax_t.fill_between(nber.index, 0, 1,\n", " where=nber['USREC']==1, \n", " color='grey', edgecolor='none',\n", " alpha=0.3, \n", " transform=ax.get_xaxis_transform(), \n", " label='NBER recession indicators')\n", "ax_t.set_ylim([0, ax_t.get_ylim()[1]])\n", "ax_t.set_xlim([start_date_graph, end_date_graph])\n", "ax_t.legend(loc='upper center',\n", " bbox_to_anchor=(0.5, 1.1),\n", " ncol=3, fontsize=9)\n", "ax_t.set_ylabel('CPI YoY change (%)')\n", "plt.show()" ] }, { "cell_type": "markdown", "id": "bf985aaa", "metadata": {}, "source": [ "We see that\n", "\n", "- consumer sentiment often remains high during expansions and\n", " drops before recessions. \n", "- there is a clear negative correlation between consumer sentiment and the CPI. \n", "\n", "\n", "When the price of consumer commodities rises, consumer confidence diminishes.\n", "\n", "This trend is more significant during [stagflation](https://en.wikipedia.org/wiki/Stagflation)." ] }, { "cell_type": "markdown", "id": "24588a53", "metadata": {}, "source": [ "### Production\n", "\n", "Real industrial output is highly correlated with recessions in the economy.\n", "\n", "However, it is not a leading indicator, as the peak of contraction in production\n", "is delayed relative to consumer confidence and inflation.\n", "\n", "We plot the real industrial output change from the previous year\n", "from 1919 to 2022 in the US to show this trend." ] }, { "cell_type": "code", "execution_count": null, "id": "1c50fade", "metadata": { "hide-output": false }, "outputs": [], "source": [ "start_date = datetime.datetime(1919, 1, 1)\n", "end_date = datetime.datetime(2022, 12, 31)\n", "\n", "nber = web.DataReader('USREC', 'fred', \n", " start_date, end_date)\n", "industrial_output = web.DataReader('INDPRO', 'fred', \n", " start_date, end_date).pct_change(12)*100\n", "\n", "fig, ax = plt.subplots()\n", "ax.plot(industrial_output, **g_params, \n", " color='#377eb8', linestyle='-', \n", " linewidth=2, label='Industrial production index')\n", "ax.fill_between(nber.index, 0, 1,\n", " where=nber['USREC']==1, \n", " color='grey', edgecolor='none',\n", " alpha=0.3, \n", " transform=ax.get_xaxis_transform(), \n", " label='NBER recession indicators')\n", "ax.set_ylim([ax.get_ylim()[0], ax.get_ylim()[1]])\n", "ax.set_ylabel('YoY real output change (%)')\n", "plt.show()" ] }, { "cell_type": "markdown", "id": "96286d58", "metadata": {}, "source": [ "We observe the delayed contraction in the plot across recessions." ] }, { "cell_type": "markdown", "id": "95b52336", "metadata": {}, "source": [ "### Credit level\n", "\n", "Credit contractions often occur during recessions, as lenders become more\n", "cautious and borrowers become more hesitant to take on additional debt.\n", "\n", "This is due to factors such as a decrease in overall economic\n", "activity and gloomy expectations for the future.\n", "\n", "One example is domestic credit to the private sector by banks in the UK.\n", "\n", "The following graph shows the domestic credit to the private sector as a\n", "percentage of GDP by banks from 1970 to 2022 in the UK." ] }, { "cell_type": "code", "execution_count": null, "id": "5808e274", "metadata": { "hide-output": false }, "outputs": [], "source": [ "private_credit = wb.data.DataFrame('FS.AST.PRVT.GD.ZS', \n", " ['GBR'], labels=True)\n", "private_credit = private_credit.set_index('Country')\n", "private_credit.columns = private_credit.columns.str.replace('YR', '').astype(int)\n", "\n", "fig, ax = plt.subplots()\n", "\n", "countries = 'United Kingdom'\n", "ylabel = 'credit level (% of GDP)'\n", "ax = plot_series(private_credit, countries, \n", " ylabel, 0.05, ax, g_params, b_params, \n", " t_params, ylim=None, baseline=None)\n", "plt.show()" ] }, { "cell_type": "markdown", "id": "fdeb7147", "metadata": {}, "source": [ "Note that the credit rises during economic expansions\n", "and stagnates or even contracts after recessions." ] } ], "metadata": { "date": 1750037598.978649, "filename": "business_cycle.md", "kernelspec": { "display_name": "Python", "language": "python3", "name": "python3" }, "title": "Business Cycles" }, "nbformat": 4, "nbformat_minor": 5 }