4 "cell_type": "markdown",
9 "Data from [European Centre for Disease Prevention and Control](https://www.ecdc.europa.eu/en/publications-data/download-todays-data-geographic-distribution-covid-19-cases-worldwide)"
21 "import collections\n",
23 "import pandas as pd\n",
24 "import numpy as np\n",
25 "from scipy.stats import gmean\n",
28 "import matplotlib as mpl\n",
29 "import matplotlib.pyplot as plt\n",
41 "DEATH_COUNT_THRESHOLD = 10\n",
42 "COUNTRIES_CORE = 'IT DE UK ES IE FR BE'.split()\n",
43 "COUNTRIES_NORDIC = 'SE NO DK FI UK'.split()\n",
44 "COUNTRIES_FRIENDS = 'IT UK ES BE SI MX'.split()\n",
45 "# COUNTRIES_FRIENDS = 'IT UK ES BE SI PT'.split()\n",
47 "COUNTRIES_AMERICAS = ['AG', 'AR', 'AW', 'BS', 'BB', 'BZ', 'BM', 'BO', 'BR', 'VG', 'KY', # excluding Canada and USA\n",
48 " 'CL', 'CO', 'CR', 'CU', 'CW', 'DM', 'DO', 'EC', 'SV', 'GL', 'GD', 'GT',\n",
49 " 'GY', 'HT', 'HN', 'JM', 'MX', 'MS', 'NI', 'PA', 'PY', 'PE', 'PR', 'KN',\n",
50 " 'LC', 'VC', 'SX', 'SR', 'TT', 'TC', 'VI', 'UY', 'VE']\n",
51 "COUNTRIES_OF_INTEREST = list(set(COUNTRIES_CORE + COUNTRIES_FRIENDS))\n",
52 "COUNTRIES_ALL = list(set(COUNTRIES_CORE + COUNTRIES_FRIENDS + COUNTRIES_NORDIC + COUNTRIES_AMERICAS))"
57 "execution_count": 4843,
64 "output_type": "stream",
66 " % Total % Received % Xferd Average Speed Time Time Time Current\n",
67 " Dload Upload Total Spent Left Speed\n",
68 "100 553k 100 553k 0 0 564k 0 --:--:-- --:--:-- --:--:-- 564k\n"
73 "!curl https://opendata.ecdc.europa.eu/covid19/casedistribution/csv/ > covid.csv"
78 "execution_count": 4844,
84 "# First col is a date, treat geoId of NA as 'Namibia', not \"NA\" value\n",
85 "raw_data = pd.read_csv('covid.csv', \n",
86 " parse_dates=[0], dayfirst=True,\n",
87 " keep_default_na=False, na_values = [''],\n",
88 "# dtype = {'day': np.int64, \n",
89 "# 'month': np.int64, \n",
90 "# 'year': np.int64, \n",
91 "# 'cases': np.int64, \n",
92 "# 'deaths': np.int64, \n",
93 "# 'countriesAndTerritories': str, \n",
95 "# 'countryterritoryCode': str, \n",
96 "# 'popData2019': np.int64, \n",
97 "# 'continentExp': str, \n",
104 "execution_count": 4845,
115 "execution_count": 4845,
117 "output_type": "execute_result"
126 "execution_count": 4846,
132 "raw_data.fillna(0, inplace=True)"
137 "execution_count": 4847,
147 " .dataframe tbody tr th:only-of-type {\n",
148 " vertical-align: middle;\n",
151 " .dataframe tbody tr th {\n",
152 " vertical-align: top;\n",
155 " .dataframe thead th {\n",
156 " text-align: right;\n",
159 "<table border=\"1\" class=\"dataframe\">\n",
161 " <tr style=\"text-align: right;\">\n",
163 " <th>dateRep</th>\n",
164 " <th>year_week</th>\n",
165 " <th>cases_weekly</th>\n",
166 " <th>deaths_weekly</th>\n",
167 " <th>countriesAndTerritories</th>\n",
169 " <th>countryterritoryCode</th>\n",
170 " <th>popData2019</th>\n",
171 " <th>continentExp</th>\n",
172 " <th>notification_rate_per_100000_population_14-days</th>\n",
178 " <td>2020-12-14</td>\n",
179 " <td>2020-50</td>\n",
182 " <td>Afghanistan</td>\n",
185 " <td>38041757.0</td>\n",
191 " <td>2020-12-07</td>\n",
192 " <td>2020-49</td>\n",
195 " <td>Afghanistan</td>\n",
198 " <td>38041757.0</td>\n",
204 " <td>2020-11-30</td>\n",
205 " <td>2020-48</td>\n",
208 " <td>Afghanistan</td>\n",
211 " <td>38041757.0</td>\n",
217 " <td>2020-11-23</td>\n",
218 " <td>2020-47</td>\n",
221 " <td>Afghanistan</td>\n",
224 " <td>38041757.0</td>\n",
230 " <td>2020-11-16</td>\n",
231 " <td>2020-46</td>\n",
234 " <td>Afghanistan</td>\n",
237 " <td>38041757.0</td>\n",
246 " dateRep year_week cases_weekly deaths_weekly countriesAndTerritories \\\n",
247 "0 2020-12-14 2020-50 1757 71 Afghanistan \n",
248 "1 2020-12-07 2020-49 1672 137 Afghanistan \n",
249 "2 2020-11-30 2020-48 1073 68 Afghanistan \n",
250 "3 2020-11-23 2020-47 1368 69 Afghanistan \n",
251 "4 2020-11-16 2020-46 1164 61 Afghanistan \n",
253 " geoId countryterritoryCode popData2019 continentExp \\\n",
254 "0 AF AFG 38041757.0 Asia \n",
255 "1 AF AFG 38041757.0 Asia \n",
256 "2 AF AFG 38041757.0 Asia \n",
257 "3 AF AFG 38041757.0 Asia \n",
258 "4 AF AFG 38041757.0 Asia \n",
260 " notification_rate_per_100000_population_14-days \n",
268 "execution_count": 4847,
270 "output_type": "execute_result"
279 "execution_count": 4848,
287 "dateRep datetime64[ns]\n",
288 "year_week object\n",
289 "cases_weekly int64\n",
290 "deaths_weekly int64\n",
291 "countriesAndTerritories object\n",
293 "countryterritoryCode object\n",
294 "popData2019 float64\n",
295 "continentExp object\n",
296 "notification_rate_per_100000_population_14-days float64\n",
300 "execution_count": 4848,
302 "output_type": "execute_result"
311 "execution_count": 4849,
318 "evalue": "'Only a column name can be used for the key in a dtype mappings argument.'",
319 "output_type": "error",
321 "\u001b[0;31m---------------------------------------------------------------------------\u001b[0m",
322 "\u001b[0;31mKeyError\u001b[0m Traceback (most recent call last)",
323 "\u001b[0;32m<ipython-input-4849-4ccdef75f4f0>\u001b[0m in \u001b[0;36m<module>\u001b[0;34m\u001b[0m\n\u001b[1;32m 9\u001b[0m \u001b[0;34m'countryterritoryCode'\u001b[0m\u001b[0;34m:\u001b[0m \u001b[0mstr\u001b[0m\u001b[0;34m,\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m 10\u001b[0m \u001b[0;34m'popData2019'\u001b[0m\u001b[0;34m:\u001b[0m \u001b[0mnp\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mint64\u001b[0m\u001b[0;34m,\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0;32m---> 11\u001b[0;31m 'continentExp': str })\n\u001b[0m",
324 "\u001b[0;32m~/anaconda3/lib/python3.7/site-packages/pandas/core/generic.py\u001b[0m in \u001b[0;36mastype\u001b[0;34m(self, dtype, copy, errors, **kwargs)\u001b[0m\n\u001b[1;32m 5855\u001b[0m \u001b[0;32mif\u001b[0m \u001b[0mcol_name\u001b[0m \u001b[0;32mnot\u001b[0m \u001b[0;32min\u001b[0m \u001b[0mself\u001b[0m\u001b[0;34m:\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m 5856\u001b[0m raise KeyError(\n\u001b[0;32m-> 5857\u001b[0;31m \u001b[0;34m\"Only a column name can be used for the \"\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0m\u001b[1;32m 5858\u001b[0m \u001b[0;34m\"key in a dtype mappings argument.\"\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m 5859\u001b[0m )\n",
325 "\u001b[0;31mKeyError\u001b[0m: 'Only a column name can be used for the key in a dtype mappings argument.'"
330 "# raw_data = raw_data.astype({'dateRep': np.datetime64, \n",
331 "# 'day': np.int64, \n",
332 "# 'month': np.int64, \n",
333 "# 'year': np.int64, \n",
334 "# 'cases': np.int64, \n",
335 "# 'deaths': np.int64, \n",
336 "# 'countriesAndTerritories': str, \n",
337 "# 'geoId': str, \n",
338 "# 'countryterritoryCode': str, \n",
339 "# 'popData2019': np.int64, \n",
340 "# 'continentExp': str })\n",
341 "raw_data = raw_data.astype({'dateRep': np.datetime64, \n",
342 " 'day': np.int64, \n",
343 " 'month': np.int64, \n",
344 " 'year': np.int64, \n",
345 " 'cases': np.int64, \n",
346 " 'deaths': np.int64, \n",
347 " 'countriesAndTerritories': str, \n",
349 " 'countryterritoryCode': str, \n",
350 " 'popData2019': np.int64, \n",
351 " 'continentExp': str })"
356 "execution_count": null,
367 "execution_count": null,
373 "raw_data[((raw_data.geoId == 'UK') & (raw_data.dateRep >= '2020-07-10'))]"
378 "execution_count": null,
384 "# raw_data = raw_data[~ ((raw_data.geoId == 'ES') & (raw_data.dateRep >= '2020-05-22'))]"
389 "execution_count": null,
395 "base_data = raw_data.set_index(['geoId', 'dateRep'])\n",
396 "base_data.sort_index(inplace=True)\n",
402 "execution_count": null,
408 "base_data.loc['ES'].loc['2020-05-10':]"
413 "execution_count": null,
419 "countries = raw_data[['geoId', 'countriesAndTerritories', 'popData2019', 'continentExp']]\n",
420 "countries = countries[countries['popData2019'] != '']\n",
421 "countries = countries.drop_duplicates()\n",
422 "countries.set_index('geoId', inplace=True)\n",
423 "countries = countries.astype({'popData2019': 'int64'})\n",
429 "execution_count": null,
440 "execution_count": null,
446 "countries[countries.countriesAndTerritories == 'Finland']"
451 "execution_count": null,
457 "countries.loc[COUNTRIES_OF_INTEREST]"
462 "execution_count": null,
468 "countries[countries.continentExp == 'America'].index"
473 "execution_count": null,
479 "data_by_date = base_data[['cases', 'deaths']]\n",
480 "data_by_date.head()"
485 "execution_count": null,
491 "data_by_date.loc['UK']"
496 "execution_count": null,
502 "# data_by_date.deaths.drop_duplicates().sort_values().to_csv('dth.csv', header=True)"
507 "execution_count": null,
513 "data_by_date.groupby(level=0).cumsum()"
518 "execution_count": null,
524 "data_by_date = data_by_date.merge(\n",
525 " data_by_date.groupby(level=0).cumsum(), \n",
526 " suffixes=('', '_culm'), \n",
527 " left_index=True, right_index=True)\n",
533 "execution_count": null,
539 "data_by_date = data_by_date.merge(\n",
540 " data_by_date[['cases', 'deaths']].groupby(level=0).diff(), \n",
541 " suffixes=('', '_diff'), \n",
542 " left_index=True, right_index=True)\n",
548 "execution_count": null,
554 "data_by_date.loc['UK', '2020-04-17']"
559 "execution_count": null,
565 "data_by_date.loc['UK']"
570 "execution_count": null,
576 "# data_by_date[data_by_date.deaths_culm > DEATH_COUNT_THRESHOLD]"
581 "execution_count": null,
587 "# days_since_threshold = data_by_date[data_by_date.deaths_culm > DEATH_COUNT_THRESHOLD].groupby(level=0).cumcount()\n",
588 "# days_since_threshold.rename('since_threshold', inplace=True)"
593 "execution_count": null,
599 "dbd = data_by_date[data_by_date.deaths_culm > DEATH_COUNT_THRESHOLD].reset_index(level=1)\n",
600 "dbd['since_threshold'] = dbd.dateRep\n",
601 "dbd.set_index('dateRep', append=True, inplace=True)\n",
602 "dbd.sort_index(inplace=True)\n",
603 "days_since_threshold = dbd.groupby(level=0).diff().since_threshold.dt.days.fillna(0).astype(int).groupby(level=0).cumsum()\n",
604 "# days_since_threshold.groupby(level=0).cumsum()\n",
606 "# days_since_threshold = dbd.rename('since_threshold')\n",
607 "days_since_threshold"
612 "execution_count": null,
618 "# days_since_threshold = (data_by_date[data_by_date.deaths_culm > DEATH_COUNT_THRESHOLD]\n",
619 "# .reset_index(level=1).groupby(level=0)\n",
620 "# .diff().dateRep.dt.days\n",
621 "# .groupby(level=0).cumcount()\n",
623 "# days_since_threshold.rename('since_threshold', inplace=True)\n",
624 "# days_since_threshold"
629 "execution_count": null,
635 "data_since_threshold = data_by_date.merge(days_since_threshold, \n",
636 " left_index=True, right_index=True)\n",
637 "data_since_threshold"
642 "execution_count": null,
648 "data_since_threshold = data_since_threshold.set_index('since_threshold', append=True\n",
649 " ).reorder_levels(['since_threshold', 'geoId', 'dateRep']\n",
650 " ).reset_index('dateRep')\n",
651 "data_since_threshold.sort_index(inplace=True)\n",
652 "data_since_threshold"
657 "execution_count": null,
663 "data_since_threshold.loc[(slice(None), ['UK', 'DE', 'IT']), :]"
668 "execution_count": null,
674 "data_since_threshold.loc[(slice(None), ['ES']), :].tail(8)"
679 "execution_count": null,
685 "data_since_threshold.loc[(slice(None), ['UK', 'DE', 'IT']), ['deaths_culm']].unstack().plot(logy=True)"
690 "execution_count": null,
696 "# deaths = data_since_threshold.loc[(slice(None), ['UK', 'DE', 'IT', 'IE']), ['deaths_culm']].unstack().xs('deaths_culm', axis=1, drop_level=True)"
701 "execution_count": null,
707 "deaths = data_since_threshold.loc[(slice(None), COUNTRIES_ALL), ['deaths_culm']].unstack().sort_index().xs('deaths_culm', axis=1, drop_level=True)\n",
708 "deaths_by_date = data_by_date.loc[COUNTRIES_ALL, ['deaths_culm']].unstack().sort_index().xs('deaths_culm', axis=1, drop_level=True).T"
713 "execution_count": null,
719 "cases = data_since_threshold.loc[(slice(None), COUNTRIES_ALL), ['cases_culm']].unstack().sort_index().xs('cases_culm', axis=1, drop_level=True)\n",
720 "cases_by_date = data_by_date.loc[ COUNTRIES_ALL, ['cases_culm']].unstack().sort_index().xs('cases_culm', axis=1, drop_level=True).T"
725 "execution_count": null,
731 "COUNTRIES_AMERICAS_DEAD = list(set(deaths.columns) & set(COUNTRIES_AMERICAS))"
736 "execution_count": null,
742 "data_since_threshold.reset_index().merge(countries, on='geoId').set_index(['since_threshold', 'geoId'])"
747 "execution_count": null,
753 "data_since_threshold.reset_index().merge(countries, on='geoId').set_index(['since_threshold', 'geoId']).sort_index(inplace=True)"
758 "execution_count": null,
764 "data_since_threshold_per_capita = data_since_threshold.reset_index().merge(countries, on='geoId').set_index(['since_threshold', 'geoId'])\n",
765 "data_since_threshold_per_capita['cases_culm_pc'] = data_since_threshold_per_capita.cases_culm / data_since_threshold_per_capita.popData2019\n",
766 "data_since_threshold_per_capita['deaths_culm_pc'] = data_since_threshold_per_capita.deaths_culm / data_since_threshold_per_capita.popData2019\n",
767 "data_since_threshold_per_capita"
772 "execution_count": null,
778 "deaths_pc = data_since_threshold_per_capita.loc[(slice(None), ['UK', 'DE', 'IT', 'IE']), ['deaths_culm_pc']].unstack().sort_index().xs('deaths_culm_pc', axis=1, drop_level=True)"
783 "execution_count": null,
794 "execution_count": null,
800 "deaths_pc = data_since_threshold_per_capita.loc[(slice(None), COUNTRIES_ALL), ['deaths_culm_pc']].unstack().xs('deaths_culm_pc', axis=1, drop_level=True)"
805 "execution_count": null,
811 "deaths[COUNTRIES_CORE].plot()"
816 "execution_count": null,
822 "deaths[COUNTRIES_FRIENDS].plot()"
827 "execution_count": null,
833 "ax = deaths[COUNTRIES_FRIENDS].plot(figsize=(10, 6), title=\"Total deaths, linear\")\n",
834 "ax.set_xlabel(f\"Days since {DEATH_COUNT_THRESHOLD} deaths\")\n",
835 "for c in COUNTRIES_FRIENDS:\n",
836 " lvi = deaths[c].last_valid_index()\n",
837 " ax.text(x = lvi + 1, y = deaths[c][lvi], s = f\"{c}: {deaths[c][lvi]:.0f}\")\n",
838 "# plt.savefig('covid_deaths_total_linear.png') "
843 "execution_count": null,
849 "ax = deaths[COUNTRIES_CORE].plot(figsize=(10, 6), title=\"Total deaths, linear\")\n",
850 "ax.set_xlabel(f\"Days since {DEATH_COUNT_THRESHOLD} deaths\")\n",
851 "for c in COUNTRIES_CORE:\n",
852 " lvi = deaths[c].last_valid_index()\n",
853 " ax.text(x = lvi + 1, y = deaths[c][lvi], s = f\"{c}: {deaths[c][lvi]:.0f}\")\n",
854 "# plt.savefig('covid_deaths_total_linear.png') "
859 "execution_count": null,
865 "ax = deaths_by_date.loc['2020-03-15':, COUNTRIES_CORE].plot(figsize=(10, 6), title=\"Total deaths, linear\")\n",
866 "# data_by_date.loc[COUNTRIES_CORE]\n",
867 "# deaths_by_date = data_by_date.loc[COUNTRIES_ALL, ['deaths_culm']].unstack().sort_index().xs('deaths_culm', axis=1, drop_level=True)\n",
868 "ax.set_xlabel(f\"Date\")\n",
869 "for c in COUNTRIES_CORE:\n",
870 " lvi = deaths_by_date[c].last_valid_index()\n",
871 " ax.text(x = lvi + pd.Timedelta(days=1), y = deaths_by_date[c][lvi], s = f\"{c}: {deaths_by_date[c][lvi]:.0f}\")\n",
872 "plt.savefig('covid_deaths_total_linear.png') "
877 "execution_count": null,
883 "deaths_prime = deaths[COUNTRIES_CORE].copy()\n",
884 "deaths_prime.loc[73:, 'ES'] = np.NaN\n",
885 "# deaths_prime['ES'][70:]"
890 "execution_count": null,
896 "ax = deaths_prime[COUNTRIES_CORE].plot(figsize=(10, 6), title=\"Total deaths, linear\")\n",
897 "for c in COUNTRIES_CORE:\n",
898 " lvi = deaths_prime[c].last_valid_index()\n",
899 " ax.text(x = lvi + 1, y = deaths_prime[c][lvi], s = f\"{c}: {deaths_prime[c][lvi]:.0f}\")\n",
900 "# plt.savefig('covid_deaths_total_linear.png') "
905 "execution_count": null,
911 "ax = cases[COUNTRIES_CORE].plot(figsize=(10, 6), title=\"Total cases, linear\")\n",
912 "for c in COUNTRIES_CORE:\n",
913 " lvi = cases[c].last_valid_index()\n",
914 " ax.text(x = lvi + 1, y = cases[c][lvi], s = c)\n",
915 "plt.savefig('covid_cases_total_linear.png') "
920 "execution_count": null,
926 "ax = deaths[COUNTRIES_AMERICAS_DEAD].plot(figsize=(10, 6), title=\"Total deaths, linear\")\n",
927 "for c in COUNTRIES_AMERICAS_DEAD:\n",
928 " lvi = deaths[c].last_valid_index()\n",
929 " ax.text(x = lvi + 1, y = deaths[c][lvi], s = c)\n",
930 "# plt.savefig('covid_deaths_total_linear.png') "
935 "execution_count": null,
941 "ax = deaths[COUNTRIES_CORE + ['BR', 'MX']].plot(figsize=(10, 6), title=\"Total deaths, linear\")\n",
942 "for c in COUNTRIES_CORE + ['BR', 'MX']:\n",
943 " lvi = deaths[c].last_valid_index()\n",
944 " ax.text(x = lvi + 1, y = deaths[c][lvi], s = c)\n",
945 "# plt.savefig('covid_deaths_total_linear.png') "
950 "execution_count": null,
956 "ax = deaths[COUNTRIES_NORDIC].plot(figsize=(10, 6), title=\"Total deaths, linear\")\n",
957 "for c in COUNTRIES_NORDIC:\n",
958 " lvi = deaths[c].last_valid_index()\n",
959 " ax.text(x = lvi + 1, y = deaths[c][lvi], s = c)\n",
960 "# plt.savefig('covid_deaths_total_linear.png') "
965 "execution_count": null,
971 "ax = deaths[COUNTRIES_OF_INTEREST].plot(figsize=(10, 6), title=\"Total deaths, linear\")\n",
972 "for c in COUNTRIES_OF_INTEREST:\n",
973 " lvi = deaths[c].last_valid_index()\n",
974 " ax.text(x = lvi + 1, y = deaths[c][lvi], s = c)\n",
975 "plt.savefig('covid_deaths_total_linear_of_interest.png') "
980 "execution_count": null,
986 "ax = deaths[COUNTRIES_CORE].plot(logy=True, figsize=(10, 6), title=\"Total deaths, log\")\n",
987 "for c in COUNTRIES_CORE:\n",
988 " lvi = deaths[c].last_valid_index()\n",
989 " ax.text(x = lvi + 1, y = deaths[c][lvi], s = c)\n",
991 "plt.savefig('covid_deaths_total_log.png')"
996 "execution_count": null,
1002 "ylim = (5*10**3, 5*10**4)\n",
1003 "ax = deaths[COUNTRIES_CORE].plot(logy=True, figsize=(10, 6), ylim=ylim, title=\"Total deaths, log\")\n",
1004 "for c in COUNTRIES_CORE:\n",
1005 " lvi = deaths[c].last_valid_index()\n",
1006 " if ylim[0] < deaths[c][lvi] < ylim[1]:\n",
1007 " ax.text(x = lvi + 1, y = deaths[c][lvi], s = c)\n",
1009 "# plt.savefig('covid_deaths_total_log.png')"
1013 "cell_type": "code",
1014 "execution_count": null,
1016 "Collapsed": "false"
1020 "ax = deaths[COUNTRIES_FRIENDS].plot(logy=True, figsize=(10, 6), title=\"Total deaths, log\")\n",
1021 "for c in COUNTRIES_FRIENDS:\n",
1022 " lvi = deaths[c].last_valid_index()\n",
1023 " ax.text(x = lvi + 1, y = deaths[c][lvi], s = c)\n",
1025 "# plt.savefig('covid_deaths_total_log.png')"
1029 "cell_type": "code",
1030 "execution_count": null,
1032 "Collapsed": "false"
1036 "ax = deaths[COUNTRIES_NORDIC].plot(logy=True, figsize=(10, 6), title=\"Total deaths, log\")\n",
1037 "for c in COUNTRIES_NORDIC:\n",
1038 " lvi = deaths[c].last_valid_index()\n",
1039 " ax.text(x = lvi + 1, y = deaths[c][lvi], s = c)\n",
1041 "# plt.savefig('covid_deaths_total_log.png')"
1045 "cell_type": "code",
1046 "execution_count": null,
1048 "Collapsed": "false"
1052 "ax = deaths[COUNTRIES_OF_INTEREST].plot(logy=True, figsize=(10, 6), title=\"Total deaths, log\")\n",
1053 "for c in COUNTRIES_OF_INTEREST:\n",
1054 " lvi = deaths[c].last_valid_index()\n",
1055 " ax.text(x = lvi + 1, y = deaths[c][lvi], s = c)\n",
1057 "plt.savefig('covid_deaths_total_log.png')"
1061 "cell_type": "code",
1062 "execution_count": null,
1064 "Collapsed": "false"
1068 "ax = deaths_pc.plot(figsize=(10, 6), title=\"Deaths per capita, linear\")\n",
1069 "for c in deaths_pc.columns:\n",
1070 " lvi = deaths_pc[c].last_valid_index()\n",
1071 " ax.text(x = lvi + 1, y = deaths_pc[c][lvi], s = c)\n",
1072 "plt.savefig('covid_deaths_per_capita_linear.png')"
1076 "cell_type": "code",
1077 "execution_count": null,
1079 "Collapsed": "false"
1083 "ax = deaths_pc.plot(logy=True, figsize=(10, 6), title=\"Deaths per capita, log\")\n",
1084 "for c in deaths_pc.columns:\n",
1085 " lvi = deaths_pc[c].last_valid_index()\n",
1086 " ax.text(x = lvi + 1, y = deaths_pc[c][lvi], s = c)"
1090 "cell_type": "code",
1091 "execution_count": null,
1093 "Collapsed": "false"
1097 "deaths_pc[['UK', 'IE']].plot( figsize=(10, 6), title=\"Deaths per capita, linear\")"
1101 "cell_type": "code",
1102 "execution_count": null,
1104 "Collapsed": "false"
1108 "deaths_pc[['UK', 'IE']].plot(logy=True, figsize=(10, 6), title=\"Deaths per capita, log\")"
1112 "cell_type": "code",
1113 "execution_count": null,
1115 "Collapsed": "false"
1119 "deaths[['UK', 'ES', 'IT']].plot(logy=True, figsize=(10, 6), title=\"Deaths, log\")\n",
1120 "plt.savefig('covid_deaths_selected_log.png')"
1124 "cell_type": "code",
1125 "execution_count": null,
1127 "Collapsed": "false"
1131 "deaths[['UK', 'ES', 'IT', 'MX']].plot(logy=True, figsize=(10, 6), title=\"Deaths, log\")"
1135 "cell_type": "code",
1136 "execution_count": null,
1138 "Collapsed": "false"
1142 "data_since_threshold.loc[(slice(None), ['UK', 'DE', 'IT']), :]"
1146 "cell_type": "code",
1147 "execution_count": null,
1149 "Collapsed": "false"
1153 "data_since_threshold['deaths_m4'] = data_since_threshold.groupby(level=1)['deaths'].transform(lambda x: x.rolling(4, 1).mean())\n",
1154 "data_since_threshold['deaths_m7'] = data_since_threshold.groupby(level=1)['deaths'].transform(lambda x: x.rolling(7, 1).mean())\n",
1155 "data_since_threshold['cases_m7'] = data_since_threshold.groupby(level=1)['cases'].transform(lambda x: x.rolling(7, 1).mean())\n",
1156 "# data_since_threshold['deaths_diff_m4'] = data_since_threshold.groupby(level=1)['deaths_diff'].transform(lambda x: x.rolling(4, 1).mean())\n",
1157 "# data_since_threshold['deaths_diff_m7'] = data_since_threshold.groupby(level=1)['deaths_diff'].transform(lambda x: x.rolling(7, 1).mean())\n",
1158 "data_since_threshold.loc[(slice(None), ['UK', 'DE', 'IT']), :]"
1162 "cell_type": "code",
1163 "execution_count": null,
1165 "Collapsed": "false"
1169 "deaths_m4 = (data_since_threshold.loc[(slice(None), COUNTRIES_ALL), ['deaths_m4']]\n",
1170 " .unstack().sort_index().xs('deaths_m4', axis=1, drop_level=True))"
1174 "cell_type": "code",
1175 "execution_count": null,
1177 "Collapsed": "false"
1181 "deaths_m7 = (data_since_threshold.loc[(slice(None), COUNTRIES_ALL), ['deaths_m7']]\n",
1182 " .unstack().sort_index().xs('deaths_m7', axis=1, drop_level=True))"
1186 "cell_type": "code",
1187 "execution_count": null,
1189 "Collapsed": "false"
1193 "cases_m7 = (data_since_threshold.loc[(slice(None), COUNTRIES_ALL), ['cases_m7']]\n",
1194 " .unstack().sort_index().xs('cases_m7', axis=1, drop_level=True))"
1198 "cell_type": "code",
1199 "execution_count": null,
1201 "Collapsed": "false"
1205 "data_by_date['cases_m7'] = data_by_date.groupby(level=0)['cases'].transform(lambda x: x.rolling(7, 1).mean())\n",
1206 "data_by_date['deaths_m7'] = data_by_date.groupby(level=0)['deaths'].transform(lambda x: x.rolling(7, 1).mean())\n",
1211 "cell_type": "code",
1212 "execution_count": null,
1214 "Collapsed": "false"
1218 "data_by_date.loc[('UK', '2020-07-15'):'UK', 'cases'].plot()"
1222 "cell_type": "code",
1223 "execution_count": null,
1225 "Collapsed": "false"
1229 "cases_by_date_m7 = data_by_date.loc[COUNTRIES_ALL, 'cases_m7'].unstack(level=0).sort_index()\n",
1230 "cases_by_date_m7[COUNTRIES_CORE].plot()"
1234 "cell_type": "code",
1235 "execution_count": null,
1237 "Collapsed": "false"
1241 "deaths_by_date_m7 = data_by_date.loc[COUNTRIES_ALL, 'deaths_m7'].unstack(level=0).sort_index()\n",
1242 "deaths_by_date_m7[COUNTRIES_CORE].plot()"
1246 "cell_type": "code",
1247 "execution_count": null,
1249 "Collapsed": "false"
1253 "ax = deaths_m4.plot(figsize=(10, 6), title=\"Deaths per day, 4 day moving average\")\n",
1254 "for c in deaths_m4.columns:\n",
1255 " lvi = deaths_m4[c].last_valid_index()\n",
1256 " ax.text(x = lvi + 1, y = deaths_m4[c][lvi], s = c)\n",
1257 "plt.savefig('covid_deaths_per_day.png') "
1261 "cell_type": "code",
1262 "execution_count": null,
1264 "Collapsed": "false"
1268 "ax = deaths_m4[COUNTRIES_CORE].plot(figsize=(10, 6), title=\"Deaths per day, 4 day moving average\")\n",
1269 "for c in COUNTRIES_CORE:\n",
1270 " lvi = deaths_m4[c].last_valid_index()\n",
1271 " ax.text(x = lvi + 1, y = deaths_m4[c][lvi], s = c)\n",
1272 "plt.savefig('covid_deaths_per_day-core.png') "
1276 "cell_type": "code",
1277 "execution_count": null,
1279 "Collapsed": "false"
1283 "ax = deaths_m4[COUNTRIES_FRIENDS].plot(figsize=(10, 6), title=\"Deaths per day, 4 day moving average\")\n",
1284 "for c in COUNTRIES_FRIENDS:\n",
1285 " lvi = deaths_m4[c].last_valid_index()\n",
1286 " ax.text(x = lvi + 1, y = deaths_m4[c][lvi], s = c)\n",
1287 "# plt.savefig('covid_deaths_per_day-friends.png') "
1291 "cell_type": "code",
1292 "execution_count": null,
1294 "Collapsed": "false"
1298 "C7s = 'ES FR IT UK'.split()\n",
1299 "ax = deaths_m7[C7s].plot(figsize=(10, 6), title=\"Deaths per day, 7 day moving average\")\n",
1301 " lvi = deaths_m7[c].last_valid_index()\n",
1302 " ax.text(x = lvi + 1, y = deaths_m7[c][lvi], s = c)\n",
1303 "# plt.savefig('covid_deaths_per_day-friends.png') "
1307 "cell_type": "code",
1308 "execution_count": null,
1310 "Collapsed": "false"
1314 "ax = deaths_m7[COUNTRIES_CORE].plot(figsize=(10, 6), title=\"Deaths per day, 7 day moving average\")\n",
1315 "ax.set_xlabel(f\"Days since {DEATH_COUNT_THRESHOLD} deaths\")\n",
1316 "for c in COUNTRIES_CORE:\n",
1317 " lvi = deaths_m7[c].last_valid_index()\n",
1318 " ax.text(x = lvi + 1, y = deaths_m7[c][lvi], s = c)\n",
1319 "# plt.axhline(0, color='0.7')\n",
1320 "plt.savefig('covid_deaths_per_day_7.png') "
1324 "cell_type": "code",
1325 "execution_count": null,
1327 "Collapsed": "false"
1331 "ax = deaths_m7[COUNTRIES_FRIENDS].plot(figsize=(10, 6), title=\"Deaths per day, 7 day moving average\")\n",
1332 "ax.set_xlabel(f\"Days since {DEATH_COUNT_THRESHOLD} deaths\")\n",
1333 "for c in COUNTRIES_FRIENDS:\n",
1334 " lvi = deaths_m7[c].last_valid_index()\n",
1335 " ax.text(x = lvi + 1, y = deaths_m7[c][lvi], s = c)\n",
1336 "# plt.axhline(0, color='0.7')\n",
1337 "plt.savefig('covid_deaths_per_day-friends.png') "
1341 "cell_type": "code",
1342 "execution_count": null,
1344 "Collapsed": "false"
1348 "deaths_m7_prime = deaths_m7[COUNTRIES_CORE].copy()\n",
1349 "deaths_m7_prime.loc[73:, 'ES'] = np.NaN\n",
1350 "deaths_m7_prime['ES'][70:]"
1354 "cell_type": "code",
1355 "execution_count": null,
1357 "Collapsed": "false"
1361 "ax = deaths_m7_prime[COUNTRIES_CORE].plot(figsize=(10, 6), title=\"Deaths per day, 7 day moving average\")\n",
1362 "for c in COUNTRIES_CORE:\n",
1363 " lvi = deaths_m7_prime[c].last_valid_index()\n",
1364 " ax.text(x = lvi + 1, y = deaths_m7_prime[c][lvi], s = c)\n",
1365 "plt.savefig('covid_deaths_per_day_7.png') # see below for where this is written, with the projection"
1369 "cell_type": "code",
1370 "execution_count": null,
1372 "Collapsed": "false"
1376 "ax = deaths_by_date_m7.loc['2020-03-01':, COUNTRIES_CORE].plot(figsize=(10, 6), title=\"Deaths per day, 7 day moving average\")\n",
1377 "ax.set_xlabel('Date')\n",
1378 "for c in COUNTRIES_CORE:\n",
1379 " lvi = deaths_by_date_m7[c].last_valid_index()\n",
1380 " ax.text(x = lvi + pd.Timedelta(days=1), y = deaths_by_date_m7[c][lvi], s = c)\n",
1381 "plt.savefig('covid_deaths_per_day_7.png') "
1385 "cell_type": "code",
1386 "execution_count": null,
1388 "Collapsed": "false"
1392 "ax = deaths_m7[COUNTRIES_FRIENDS].plot(figsize=(10, 6), title=\"Deaths per day, 7 day moving average\")\n",
1393 "for c in COUNTRIES_FRIENDS:\n",
1394 " lvi = deaths_m7[c].last_valid_index()\n",
1395 " ax.text(x = lvi + 1, y = deaths_m7[c][lvi], s = c)\n",
1396 "plt.savefig('covid_deaths_per_day_friends_7.png') "
1400 "cell_type": "code",
1401 "execution_count": null,
1403 "Collapsed": "false"
1407 "ax = deaths_m7[COUNTRIES_CORE + ['BR', 'MX']].plot(figsize=(10, 6), title=\"Deaths per day, 7 day moving average\")\n",
1408 "for c in COUNTRIES_CORE + ['BR', 'MX']:\n",
1409 " lvi = deaths_m7[c].last_valid_index()\n",
1410 " ax.text(x = lvi + 1, y = deaths_m7[c][lvi], s = c)\n",
1411 "# plt.savefig('covid_deaths_per_day_7.png') "
1415 "cell_type": "code",
1416 "execution_count": null,
1418 "Collapsed": "false"
1422 "ax = deaths_by_date_m7.iloc[-30:][COUNTRIES_CORE].plot(figsize=(10, 6), title=\"Deaths per day, 7 day moving average\")#, ylim=(-10, 100))\n",
1423 "ax.set_xlabel(\"Date\")\n",
1425 "text_x_pos = deaths_by_date_m7.last_valid_index() + pd.Timedelta(days=1)\n",
1427 "for c in COUNTRIES_CORE:\n",
1428 " lvi = deaths_by_date_m7[c].last_valid_index()\n",
1429 "# if c != 'ES':\n",
1430 " ax.text(x = text_x_pos, y = deaths_by_date_m7[c][lvi], s = f\"{c}: {deaths_by_date_m7[c][lvi]:.0f}\")\n",
1431 "plt.savefig('deaths_by_date_last_30_days.png') "
1435 "cell_type": "code",
1436 "execution_count": null,
1438 "Collapsed": "false"
1442 "ax = deaths_by_date_m7.iloc[-30:][COUNTRIES_FRIENDS].plot(figsize=(10, 6), title=\"Deaths per day, 7 day moving average\")#, ylim=(-10, 100))\n",
1443 "ax.set_xlabel(\"Date\")\n",
1445 "text_x_pos = deaths_by_date_m7.last_valid_index() + pd.Timedelta(days=1)\n",
1447 "for c in COUNTRIES_FRIENDS:\n",
1448 " lvi = deaths_by_date_m7[c].last_valid_index()\n",
1449 "# if c != 'ES':\n",
1450 " ax.text(x = text_x_pos, y = deaths_by_date_m7[c][lvi], s = f\"{c}: {deaths_by_date_m7[c][lvi]:.0f}\")\n",
1451 "plt.savefig('deaths_by_date_last_30_days_friends.png') "
1455 "cell_type": "code",
1456 "execution_count": null,
1458 "Collapsed": "false"
1462 "ax = cases_m7[COUNTRIES_CORE].plot(figsize=(10, 6), title=\"Cases per day, 7 day moving average\")\n",
1463 "for c in COUNTRIES_CORE:\n",
1464 " lvi = cases_m7[c].last_valid_index()\n",
1465 " ax.text(x = lvi + 1, y = cases_m7[c][lvi], s = c)\n",
1466 "plt.savefig('covid_cases_per_day-core.png') "
1470 "cell_type": "code",
1471 "execution_count": null,
1473 "Collapsed": "false"
1477 "ax = cases_m7[COUNTRIES_FRIENDS].plot(figsize=(10, 6), title=\"Cases per day, 7 day moving average\")\n",
1478 "for c in COUNTRIES_FRIENDS:\n",
1479 " lvi = cases_m7[c].last_valid_index()\n",
1480 " ax.text(x = lvi + 1, y = cases_m7[c][lvi], s = c)\n",
1481 "plt.savefig('covid_cases_per_day-core.png') "
1485 "cell_type": "code",
1486 "execution_count": null,
1488 "Collapsed": "false"
1492 "ax = cases_by_date_m7.iloc[-30:][COUNTRIES_FRIENDS].plot(figsize=(10, 6), title=\"Cases per day, 7 day moving average\")#, ylim=(-10, 100))\n",
1493 "ax.set_xlabel(\"Date\")\n",
1495 "text_x_pos = cases_by_date_m7.last_valid_index() + pd.Timedelta(days=1)\n",
1497 "for c in COUNTRIES_FRIENDS:\n",
1498 " lvi = cases_by_date_m7[c].last_valid_index()\n",
1499 "# if c != 'ES':\n",
1500 " ax.text(x = text_x_pos, y = cases_by_date_m7[c][lvi], s = f\"{c}: {cases_by_date_m7[c][lvi]:.0f}\")\n",
1501 "plt.savefig('cases_by_date_last_30_days_friends.png') "
1505 "cell_type": "code",
1506 "execution_count": null,
1508 "Collapsed": "false"
1512 "def gmean_scale(items):\n",
1513 " return gmean(items) / items[-1]"
1517 "cell_type": "code",
1518 "execution_count": null,
1520 "Collapsed": "false"
1524 "def doubling_time(df):\n",
1525 " return np.log(2) / np.log((df.deaths_culm + df.deaths_g4) / df.deaths_culm)\n",
1527 "def doubling_time_7(df):\n",
1528 " return np.log(2) / np.log((df.deaths_culm + df.deaths_g7) / df.deaths_culm)"
1532 "cell_type": "code",
1533 "execution_count": null,
1535 "Collapsed": "false"
1539 "# data_since_threshold['deaths_g4'] = data_since_threshold.groupby(level=1)['deaths'].transform(lambda x: x.rolling(4, 1).apply(gmean_scale, raw=True))\n",
1540 "# data_since_threshold.loc[(slice(None), ['UK', 'DE', 'IT']), :]"
1544 "cell_type": "code",
1545 "execution_count": null,
1547 "Collapsed": "false"
1551 "data_since_threshold['deaths_g4'] = data_since_threshold.groupby(level=1)['deaths'].transform(lambda x: x.rolling(4, 1).apply(gmean, raw=True))\n",
1552 "data_since_threshold['deaths_g7'] = data_since_threshold.groupby(level=1)['deaths'].transform(lambda x: x.rolling(7, 1).apply(gmean, raw=True))\n",
1553 "data_since_threshold.loc[(slice(None), ['UK', 'DE', 'IT']), :]"
1557 "cell_type": "code",
1558 "execution_count": null,
1560 "Collapsed": "false"
1564 "data_since_threshold['doubling_time'] = data_since_threshold.groupby(level=1).apply(doubling_time).reset_index(level=0, drop=True).sort_index()\n",
1565 "data_since_threshold['doubling_time_7'] = data_since_threshold.groupby(level=1).apply(doubling_time_7).reset_index(level=0, drop=True).sort_index()\n",
1566 "# data_since_threshold.loc[(slice(None), 'UK'), :]"
1570 "cell_type": "code",
1571 "execution_count": null,
1573 "Collapsed": "false"
1577 "data_by_date['deaths_g4'] = data_by_date.groupby(level=0)['deaths'].transform(lambda x: x.rolling(4, 1).apply(gmean, raw=True))\n",
1578 "data_by_date['deaths_g7'] = data_by_date.groupby(level=0)['deaths'].transform(lambda x: x.rolling(7, 1).apply(gmean, raw=True))\n",
1579 "data_by_date['doubling_time'] = data_by_date.groupby(level=0).apply(doubling_time).reset_index(level=0, drop=True).sort_index()\n",
1580 "data_by_date['doubling_time_7'] = data_by_date.groupby(level=0).apply(doubling_time_7).reset_index(level=0, drop=True).sort_index()\n",
1581 "data_by_date.loc['UK']"
1585 "cell_type": "code",
1586 "execution_count": null,
1588 "Collapsed": "false"
1592 "doubling_times = (data_since_threshold.loc[(slice(None), COUNTRIES_OF_INTEREST), ['doubling_time']]\n",
1593 " .unstack().sort_index().xs('doubling_time', axis=1, drop_level=True))\n",
1594 "doubling_times.replace([np.inf, -np.inf], np.nan, inplace=True)"
1598 "cell_type": "code",
1599 "execution_count": null,
1601 "Collapsed": "false"
1605 "doubling_times_7 = (data_since_threshold.loc[(slice(None), COUNTRIES_OF_INTEREST), ['doubling_time_7']]\n",
1606 " .unstack().sort_index().xs('doubling_time_7', axis=1, drop_level=True))\n",
1607 "doubling_times_7.replace([np.inf, -np.inf], np.nan, inplace=True)"
1611 "cell_type": "code",
1612 "execution_count": null,
1614 "Collapsed": "false"
1618 "ax = doubling_times.plot(figsize=(10, 6), title=\"Doubling times, 4 day average\")\n",
1619 "for c in doubling_times.columns:\n",
1620 " lvi = doubling_times[c].last_valid_index()\n",
1621 " ax.text(x = lvi + 1, y = doubling_times[c][lvi], s = c)\n",
1622 "# plt.savefig('covid_deaths_per_day.png') "
1626 "cell_type": "code",
1627 "execution_count": null,
1629 "Collapsed": "false"
1633 "ax = doubling_times_7[COUNTRIES_CORE].plot(figsize=(10, 6), title=\"Doubling times, 7 day average\")\n",
1634 "ax.legend(loc=\"upper left\")\n",
1635 "for c in COUNTRIES_CORE:\n",
1636 " lvi = doubling_times_7[c].last_valid_index()\n",
1637 " ax.text(x = lvi + 1, y = doubling_times_7[c][lvi], s = c)\n",
1638 "plt.savefig('covid_doubling_times_7.png') "
1642 "cell_type": "code",
1643 "execution_count": null,
1645 "Collapsed": "false"
1649 "ax = doubling_times[COUNTRIES_CORE].plot(figsize=(10, 6), title=\"Doubling times, 4 day average\")\n",
1650 "for c in COUNTRIES_CORE:\n",
1651 " lvi = doubling_times[c].last_valid_index()\n",
1652 " ax.text(x = lvi + 1, y = doubling_times[c][lvi], s = c)\n",
1653 "plt.savefig('covid_doubling_times.png') "
1657 "cell_type": "code",
1658 "execution_count": null,
1660 "Collapsed": "false"
1664 "ax = doubling_times[COUNTRIES_FRIENDS].plot(figsize=(10, 6), title=\"Doubling times\")\n",
1665 "for c in COUNTRIES_FRIENDS:\n",
1666 " lvi = doubling_times[c].last_valid_index()\n",
1667 " ax.text(x = lvi + 1, y = doubling_times[c][lvi], s = c)\n",
1668 "plt.savefig('covid_doubling_times_friends.png')"
1672 "cell_type": "code",
1673 "execution_count": null,
1675 "Collapsed": "false"
1679 "ax = doubling_times[C7s].plot(figsize=(10, 6), title=\"Doubling times\")\n",
1681 " lvi = doubling_times[c].last_valid_index()\n",
1682 " ax.text(x = lvi + 1, y = doubling_times[c][lvi], s = c)\n",
1683 "# plt.savefig('covid_doubling_times_friends.png')"
1687 "cell_type": "code",
1688 "execution_count": null,
1690 "Collapsed": "false"
1694 "# deaths_diff_m4 = (data_since_threshold.loc[(slice(None), COUNTRIES_ALL), ['deaths_diff_m4']]\n",
1695 "# .unstack().sort_index().xs('deaths_diff_m4', axis=1, drop_level=True))"
1699 "cell_type": "code",
1700 "execution_count": null,
1702 "Collapsed": "false"
1706 "# deaths_diff_m7 = (data_since_threshold.loc[(slice(None), COUNTRIES_ALL), ['deaths_diff_m7']]\n",
1707 "# .unstack().sort_index().xs('deaths_diff_m7', axis=1, drop_level=True))"
1711 "cell_type": "code",
1712 "execution_count": null,
1714 "Collapsed": "false"
1722 "cell_type": "code",
1723 "execution_count": null,
1725 "Collapsed": "false"
1729 "# data_since_threshold.replace([np.inf, -np.inf], np.nan).groupby(level=1).last().loc[COUNTRIES_ALL]#, [doubling_time]]"
1733 "cell_type": "code",
1734 "execution_count": null,
1736 "Collapsed": "false"
1740 "dstl = data_since_threshold.replace([np.inf, -np.inf], np.nan).groupby(level=1).last()\n",
1741 "dstl.loc[dstl.index.intersection(COUNTRIES_ALL)]"
1745 "cell_type": "code",
1746 "execution_count": null,
1748 "Collapsed": "false"
1752 "# data_since_threshold.replace([np.inf, -np.inf], np.nan).groupby(level=1).last().loc[['UK', 'DE', 'IT']]#, [doubling_time]]\n",
1753 "dstl.loc[['UK', 'DE', 'IT', 'FR', 'ES']]"
1757 "cell_type": "code",
1758 "execution_count": null,
1760 "Collapsed": "false"
1764 "data_since_threshold.loc[(slice(None), ['UK']), :].tail(20)"
1768 "cell_type": "code",
1769 "execution_count": null,
1771 "Collapsed": "false"
1775 "data_since_threshold.loc[(slice(None), ['ES']), :].tail(20)"
1779 "cell_type": "markdown",
1781 "Collapsed": "false"
1784 "## Death projections"
1788 "cell_type": "code",
1789 "execution_count": null,
1791 "Collapsed": "false"
1795 "data_since_threshold.loc[(slice(None), ['UK']), :].tail(15)"
1799 "cell_type": "code",
1800 "execution_count": null,
1802 "Collapsed": "false"
1806 "it_since_threshold = data_since_threshold.replace([np.inf, -np.inf], np.nan).loc[(slice(None), ['IT']), :]\n",
1807 "s_end = it_since_threshold.index.max()[0]\n",
1812 "cell_type": "code",
1813 "execution_count": null,
1815 "Collapsed": "false"
1819 "uk_projection = data_since_threshold.replace([np.inf, -np.inf], np.nan).loc[(slice(None), ['UK']), :]\n",
1820 "uk_current_end = uk_projection.index.max()[0] + 1\n",
1821 "# s_start = uk_projection.index.max()[0] + 1\n",
1826 "cell_type": "code",
1827 "execution_count": null,
1829 "Collapsed": "false"
1833 "current_uk_deaths_m7 = uk_projection[uk_projection.deaths_m7 >= 0].iloc[-1].deaths_m7\n",
1834 "current_uk_deaths_m7"
1838 "cell_type": "code",
1839 "execution_count": null,
1841 "Collapsed": "false"
1845 "it_since_threshold[it_since_threshold.deaths_m7 <= current_uk_deaths_m7].loc[60:].first_valid_index()[0]"
1849 "cell_type": "code",
1850 "execution_count": null,
1852 "Collapsed": "false"
1856 "s_start = it_since_threshold[it_since_threshold.deaths_m7 <= current_uk_deaths_m7].loc[60:].first_valid_index()[0]\n",
1861 "cell_type": "code",
1862 "execution_count": null,
1864 "Collapsed": "false"
1868 "s_start_date = data_since_threshold.loc[(89, 'IT'), 'dateRep']# .iloc[0]\n",
1873 "cell_type": "code",
1874 "execution_count": null,
1876 "Collapsed": "false"
1884 "cell_type": "code",
1885 "execution_count": null,
1887 "Collapsed": "false"
1891 "uk_end = s_end - s_start + uk_current_end\n",
1896 "cell_type": "code",
1897 "execution_count": null,
1899 "Collapsed": "false"
1903 "proj = it_since_threshold.loc[(slice(s_start, s_end), slice(None)), ['cases', 'deaths', 'deaths_m7']]\n",
1904 "ndiff = uk_current_end - s_start\n",
1905 "proj.index = pd.MultiIndex.from_tuples([(n + ndiff, 'UK') for n, _ in proj.index], names=proj.index.names)\n",
1910 "cell_type": "code",
1911 "execution_count": null,
1913 "Collapsed": "false"
1917 "it_since_threshold.loc[(slice(s_start - 8, s_start + 2), slice(None)), ['cases', 'deaths', 'deaths_m7']]"
1921 "cell_type": "code",
1922 "execution_count": null,
1924 "Collapsed": "false"
1928 "uk_projection[['cases', 'deaths', 'deaths_m7']].tail()"
1932 "cell_type": "code",
1933 "execution_count": null,
1935 "Collapsed": "false"
1939 "# proj['deaths_m7'] = proj['deaths_m7'] + 20\n",
1944 "cell_type": "markdown",
1946 "Collapsed": "false"
1949 "Projected deaths, UK following IT trend from now."
1953 "cell_type": "code",
1954 "execution_count": null,
1956 "Collapsed": "false"
1960 "uk_projection = uk_projection.append(proj, sort=True)\n",
1961 "uk_projection.deaths.sum()"
1965 "cell_type": "code",
1966 "execution_count": null,
1968 "Collapsed": "false"
1972 "uk_projection = uk_projection.droplevel(1)\n",
1977 "cell_type": "code",
1978 "execution_count": null,
1980 "Collapsed": "false"
1984 "uk_projection.loc[152, 'deaths']"
1988 "cell_type": "markdown",
1990 "Collapsed": "false"
1993 "## Correction for cumulative deaths correction on 14 August"
1997 "cell_type": "code",
1998 "execution_count": null,
2000 "Collapsed": "false"
2004 "# uk_projection.loc[152, 'deaths'] = 50"
2008 "cell_type": "code",
2009 "execution_count": null,
2011 "Collapsed": "false"
2015 "uk_projection['deaths_m7'] = uk_projection['deaths'].transform(lambda x: x.rolling(7, 1).mean())\n",
2016 "uk_projection.loc[(uk_current_end - 20):(uk_current_end + 5)]"
2020 "cell_type": "code",
2021 "execution_count": null,
2023 "Collapsed": "false"
2027 "uk_projection.loc[(uk_current_end - 5):]"
2031 "cell_type": "code",
2032 "execution_count": null,
2034 "Collapsed": "false"
2038 "uk_projection.deaths_m7.plot()"
2042 "cell_type": "code",
2043 "execution_count": null,
2045 "Collapsed": "false"
2049 "proj.droplevel(level=1)"
2053 "cell_type": "code",
2054 "execution_count": null,
2056 "Collapsed": "false"
2060 "ax = deaths_m7[COUNTRIES_CORE].plot()\n",
2061 "# uk_projection['deaths_m7'].plot(figsize=(10, 6), title=\"Deaths per day, 7 day moving average\", label=\"Projection\", style='--', ax=ax)\n",
2062 "proj.droplevel(level=1)['deaths_m7'].plot(figsize=(10, 6), title=\"Deaths per day, 7 day moving average\", label=\"Projection\", style='--', ax=ax)\n",
2063 "ax.set_xlabel(f\"Days since {DEATH_COUNT_THRESHOLD} deaths\")\n",
2064 "for c in COUNTRIES_CORE:\n",
2065 " lvi = deaths_m7[c].last_valid_index()\n",
2066 " ax.text(x = lvi + 1, y = deaths_m7[c][lvi], s = c)\n",
2067 "# plt.savefig('covid_deaths_per_day_7.png') "
2071 "cell_type": "code",
2072 "execution_count": null,
2074 "Collapsed": "false"
2078 "it_since_threshold.deaths.sum()"
2082 "cell_type": "markdown",
2084 "Collapsed": "false"
2087 "# Excess deaths calculation"
2091 "cell_type": "code",
2092 "execution_count": null,
2094 "Collapsed": "false"
2098 "with open('excess_deaths.json') as f:\n",
2099 " excess_deaths_data = json.load(f)\n",
2101 "# with open('excess_death_accuracy.json') as f:\n",
2102 "# excess_death_accuracy = json.load(f)\n",
2104 "excess_deaths_data"
2108 "cell_type": "code",
2109 "execution_count": null,
2111 "Collapsed": "false"
2115 "additional_deaths = data_by_date.loc[('UK', excess_deaths_data['end_date']):('UK')].iloc[1:].deaths.sum()\n",
2120 "cell_type": "code",
2121 "execution_count": null,
2123 "Collapsed": "false"
2127 "uk_covid_deaths = data_by_date.loc['UK'].deaths.sum()\n",
2132 "cell_type": "code",
2133 "execution_count": null,
2135 "Collapsed": "false"
2139 "uk_deaths_to_date = int(excess_deaths_data['excess_deaths']) + additional_deaths\n",
2144 "cell_type": "code",
2145 "execution_count": null,
2147 "Collapsed": "false"
2151 "# excess_deaths_upto = '2020-05-08'\n",
2152 "# excess_deaths = 54500"
2156 "cell_type": "code",
2157 "execution_count": null,
2159 "Collapsed": "false"
2163 "# excess_deaths_upto = excess_deaths_data['end_date']\n",
2164 "# excess_deaths = excess_deaths_data['excess_deaths']"
2168 "cell_type": "markdown",
2170 "Collapsed": "false"
2173 "Recorded deaths in period where ONS has reported total deaths"
2177 "cell_type": "code",
2178 "execution_count": null,
2180 "Collapsed": "false"
2184 "# ons_reported_deaths = base_data.loc['UK'][:excess_deaths_upto]['deaths'].sum()\n",
2185 "# ons_reported_deaths"
2189 "cell_type": "code",
2190 "execution_count": null,
2192 "Collapsed": "false"
2196 "# excess_deaths_upto"
2200 "cell_type": "markdown",
2202 "Collapsed": "false"
2205 "## Correction for deaths total correction on 14 August"
2209 "cell_type": "code",
2210 "execution_count": null,
2212 "Collapsed": "false"
2216 "# ons_unreported_deaths_data = base_data.loc['UK'][excess_deaths_upto:].iloc[1:]['deaths']\n",
2217 "# ons_unreported_deaths_data['2020-08-14'] = 50"
2221 "cell_type": "code",
2222 "execution_count": null,
2224 "Collapsed": "false"
2228 "# ons_unreported_deaths = ons_unreported_deaths_data.sum()\n",
2229 "# ons_unreported_deaths"
2233 "cell_type": "code",
2234 "execution_count": null,
2236 "Collapsed": "false"
2240 "# scaled_ons_unreported_deaths = ons_unreported_deaths * excess_death_accuracy\n",
2241 "# scaled_ons_unreported_deaths"
2245 "cell_type": "code",
2246 "execution_count": null,
2248 "Collapsed": "false"
2252 "# uk_deaths_to_date = excess_deaths + scaled_ons_unreported_deaths\n",
2253 "# uk_deaths_to_date"
2257 "cell_type": "code",
2258 "execution_count": null,
2260 "Collapsed": "false"
2264 "# data_since_threshold.loc[(slice(None), 'UK'), :][data_since_threshold.dateRep == excess_deaths_data['end_date']]"
2268 "cell_type": "code",
2269 "execution_count": null,
2271 "Collapsed": "false"
2275 "# data_since_threshold[data_since_threshold.dateRep == excess_deaths_data['end_date']].loc[(slice(None), 'UK'), :]"
2279 "cell_type": "code",
2280 "execution_count": null,
2282 "Collapsed": "false"
2286 "# ons_unreported_start = data_since_threshold[data_since_threshold.dateRep == excess_deaths_data['end_date']].loc[(slice(None), 'UK'), :].first_valid_index()[0] + 1\n",
2287 "# ons_unreported_start"
2291 "cell_type": "code",
2292 "execution_count": null,
2294 "Collapsed": "false"
2298 "# unreported_projected_deaths = uk_projection.loc[ons_unreported_start:].deaths.sum()\n",
2299 "# unreported_projected_deaths"
2303 "cell_type": "code",
2304 "execution_count": null,
2306 "Collapsed": "false"
2310 "# unreported_projected_deaths_scaled = unreported_projected_deaths * excess_death_accuracy\n",
2311 "# unreported_projected_deaths_scaled"
2315 "cell_type": "code",
2316 "execution_count": null,
2318 "Collapsed": "false"
2322 "# uk_projection.loc[(s_start):].deaths.sum()"
2326 "cell_type": "code",
2327 "execution_count": null,
2329 "Collapsed": "false"
2333 "# deaths_actual_projected_scaled = uk_deaths_to_date + uk_projection.loc[(s_start):].deaths.sum() * excess_death_accuracy\n",
2334 "# deaths_actual_projected_scaled"
2338 "cell_type": "code",
2339 "execution_count": null,
2341 "Collapsed": "false"
2345 "# excess_deaths / reported_deaths"
2349 "cell_type": "markdown",
2351 "Collapsed": "false"
2354 "True deaths to date, if we follow the scaling of excess deaths over reported deaths so far."
2358 "cell_type": "code",
2359 "execution_count": null,
2361 "Collapsed": "false"
2365 "# uk_covid_deaths = data_since_threshold.replace([np.inf, -np.inf], np.nan).loc[(slice(None), ['UK']), 'deaths_culm'].iloc[-1]\n",
2370 "cell_type": "code",
2371 "execution_count": null,
2373 "Collapsed": "false"
2377 "# uk_covid_deaths_scaled = excess_deaths + unreported_deaths * excess_death_accuracy\n",
2378 "# uk_covid_deaths_scaled"
2382 "cell_type": "code",
2383 "execution_count": null,
2385 "Collapsed": "false"
2389 "# data_since_threshold.replace([np.inf, -np.inf], np.nan).loc[(slice(None), ['IT']), 'dateRep'].iloc[-1] + pd.Timedelta(s_end - s_start, unit='days')"
2393 "cell_type": "code",
2394 "execution_count": null,
2396 "Collapsed": "false"
2400 "# data_since_threshold.replace([np.inf, -np.inf], np.nan).loc[(slice(None), ['UK']), 'dateRep'].iloc[-1].strftime(\"%Y-%m-%d\")"
2404 "cell_type": "code",
2405 "execution_count": null,
2407 "Collapsed": "false"
2411 "# uk_covid_deaths * excess_deaths / reported_deaths"
2415 "cell_type": "code",
2416 "execution_count": null,
2418 "Collapsed": "false"
2422 "# uk_projection.deaths.sum() * excess_deaths / reported_deaths"
2426 "cell_type": "code",
2427 "execution_count": null,
2429 "Collapsed": "false"
2433 "# data_since_threshold.loc[(slice(None), 'FR'), :]\n",
2434 "# data_since_threshold[data_since_threshold.dateRep == '2020-05-18'].loc[(slice(None), 'FR'), :]"
2438 "cell_type": "markdown",
2440 "Collapsed": "false"
2443 "## School reopenings"
2447 "cell_type": "code",
2448 "execution_count": null,
2450 "Collapsed": "false"
2454 "school_reopenings = {\n",
2455 " 'ES': {'date': '2020-05-18'},\n",
2456 " 'FR': {'date': '2020-05-18'}, # some areas only\n",
2457 "# 'IT': {'date': '2020-09-01'},\n",
2458 " # 'IE': {'date': '2020-09-01'},\n",
2459 " 'DE': {'date': '2020-05-04'},\n",
2460 " 'UK': {'date': '2020-06-01'}\n",
2465 "cell_type": "code",
2466 "execution_count": null,
2468 "Collapsed": "false"
2472 "data_since_threshold[data_since_threshold.dateRep == '2020-05-04'].loc[(slice(None), ['DE']), :].first_valid_index()"
2476 "cell_type": "code",
2477 "execution_count": null,
2479 "Collapsed": "false"
2483 "data_since_threshold[data_since_threshold.dateRep == '2020-05-04'].loc[(slice(None), ['DE']), :].iloc[0].deaths_m7"
2487 "cell_type": "code",
2488 "execution_count": null,
2490 "Collapsed": "false"
2494 "for cID in school_reopenings:\n",
2495 " dst_in = data_since_threshold[data_since_threshold.dateRep == (school_reopenings[cID]['date'])].loc[(slice(None), [cID]), :]\n",
2496 " dst_i = dst_in.first_valid_index()\n",
2497 " dst_n = dst_in.iloc[0].deaths_m7\n",
2498 " school_reopenings[cID]['since_threshold'] = dst_i[0]\n",
2499 " school_reopenings[cID]['deaths_m7'] = dst_n\n",
2504 "cell_type": "code",
2505 "execution_count": null,
2507 "Collapsed": "false"
2511 "ax = deaths_m7[COUNTRIES_CORE].plot(figsize=(15, 9), title=\"Deaths per day, 7 day moving average\")\n",
2512 "# uk_projection.deaths_m7.plot(ax=ax)\n",
2513 "for c in COUNTRIES_CORE:\n",
2514 " lvi = deaths_m7[c].last_valid_index()\n",
2515 " ax.text(x = lvi + 1, y = deaths_m7[c][lvi], s = f\"{c}: {deaths_m7[c][lvi]:.0f}\")\n",
2516 " if c in school_reopenings:\n",
2517 " marker_col = [l for l in ax.lines if l.get_label() == c][0].get_color()\n",
2518 " ax.plot(school_reopenings[c]['since_threshold'], school_reopenings[c]['deaths_m7'], '*', \n",
2519 " markersize=18, markerfacecolor=marker_col, markeredgecolor=marker_col)\n",
2520 " ax.text(x = school_reopenings[c]['since_threshold'] + 1, y = school_reopenings[c]['deaths_m7'], \n",
2521 " s = f\"{school_reopenings[c]['date']}: {school_reopenings[c]['deaths_m7']:.0f}\")\n",
2522 "plt.savefig('school_reopenings.png')"
2526 "cell_type": "code",
2527 "execution_count": null,
2529 "Collapsed": "false"
2533 "# ax = deaths_m7[COUNTRIES_CORE].plot(figsize=(15, 9), title=\"Deaths per day, 7 day moving average\",\n",
2534 "# xlim=(46, 91), ylim=(0, 400))\n",
2535 "# # uk_projection.deaths_m7.plot(ax=ax)\n",
2536 "# for c in COUNTRIES_CORE:\n",
2537 "# lvi = deaths_m7[c].last_valid_index()\n",
2538 "# ax.text(x = lvi + 1, y = deaths_m7[c][lvi], s = f\"{c}: {deaths_m7[c][lvi]:.0f}\", fontsize=14)\n",
2539 "# if c in school_reopenings:\n",
2540 "# marker_col = [l for l in ax.lines if l.get_label() == c][0].get_color()\n",
2541 "# ax.plot(school_reopenings[c]['since_threshold'], school_reopenings[c]['deaths_m7'], '*', \n",
2542 "# markersize=18, markerfacecolor=marker_col, markeredgecolor=marker_col)\n",
2543 "# ax.text(x = school_reopenings[c]['since_threshold'] + 1, y = school_reopenings[c]['deaths_m7'], \n",
2544 "# s = f\"{school_reopenings[c]['date']}: {school_reopenings[c]['deaths_m7']:.0f}\",\n",
2546 "# plt.savefig('school_reopenings_detail.png')"
2550 "cell_type": "markdown",
2552 "Collapsed": "false"
2559 "cell_type": "code",
2560 "execution_count": null,
2562 "Collapsed": "false"
2566 "lockdown_dates = {\n",
2567 " 'ES': { 'part_start': {'date': '2020-03-14'}\n",
2568 " , 'full_start': {'date': '2020-03-15'}\n",
2569 " , 'part_finish': {'date': '2020-05-18'}\n",
2571 " 'FR': { 'part_start': {'date': '2020-03-13'}\n",
2572 " , 'full_start': {'date': '2020-03-17'}\n",
2573 " , 'part_finish': {'date': '2020-05-11'}\n",
2575 " 'IT': { 'part_start': {'date': '2020-03-08'}\n",
2576 " , 'full_start': {'date': '2020-03-10'}\n",
2577 " , 'part_finish': {'date': '2020-05-04'}\n",
2579 " 'DE': { #'part_start': {'date': '2020-03-13'}\n",
2580 " 'full_start': {'date': '2020-03-22'}\n",
2581 " , 'part_finish': {'date': '2020-05-06'}\n",
2583 " 'UK': { 'part_start': {'date': '2020-03-23'}\n",
2584 " , 'full_start': {'date': '2020-03-23'}\n",
2585 " , 'part_finish': {'date': '2020-05-31'}\n",
2587 " 'IE': { #'part_start': {'date': '2020-03-12'}\n",
2588 " 'full_start': {'date': '2020-03-27'}\n",
2589 " , 'part_finish': {'date': '2020-05-18'}\n",
2595 "cell_type": "code",
2596 "execution_count": null,
2598 "Collapsed": "false"
2602 "for cID in lockdown_dates:\n",
2603 " for phase in lockdown_dates[cID]:\n",
2604 " dst_in = data_since_threshold[data_since_threshold.dateRep == (lockdown_dates[cID][phase]['date'])].loc[(slice(None), [cID]), :]\n",
2605 " dst_i = dst_in.first_valid_index()\n",
2606 " dst_n = dst_in.iloc[0].deaths_m7\n",
2607 " dst_c = dst_in.iloc[0].cases_m7\n",
2608 " lockdown_dates[cID][phase]['since_threshold'] = dst_i[0]\n",
2609 " lockdown_dates[cID][phase]['deaths_m7'] = dst_n\n",
2610 " lockdown_dates[cID][phase]['cases_m7'] = dst_c\n",
2616 "cell_type": "code",
2617 "execution_count": null,
2619 "Collapsed": "false"
2623 "ax = deaths_m7[COUNTRIES_CORE].plot(figsize=(15, 9), title=\"Deaths per day, 7 day moving averagee, with lockdown dates\")\n",
2624 "ax.set_xlabel(f\"Days since {DEATH_COUNT_THRESHOLD} deaths\")\n",
2625 "# uk_projection.deaths_m7.plot(ax=ax)\n",
2626 "for c in COUNTRIES_CORE:\n",
2627 " lvi = deaths_m7[c].last_valid_index()\n",
2629 " ax.text(x = lvi + 1, y = deaths_m7[c][lvi], s = f\"{c}: {deaths_m7[c][lvi]:.0f}\")\n",
2630 " if c in lockdown_dates:\n",
2631 " for phase in lockdown_dates[c]:\n",
2632 " marker_col = [l for l in ax.lines if l.get_label() == c][0].get_color()\n",
2633 " ax.plot(lockdown_dates[c][phase]['since_threshold'], lockdown_dates[c][phase]['deaths_m7'], '*',\n",
2634 " markersize=18, markerfacecolor=marker_col, markeredgecolor=marker_col)\n",
2635 " if 'start' not in phase:\n",
2636 " ax.text(x = lockdown_dates[c][phase]['since_threshold'] + 1, y = lockdown_dates[c][phase]['deaths_m7'], \n",
2637 " s = f\"{lockdown_dates[c][phase]['date']}: {lockdown_dates[c][phase]['deaths_m7']:.0f}\")\n",
2638 "# plt.savefig('school_reopenings.png')"
2642 "cell_type": "code",
2643 "execution_count": null,
2645 "Collapsed": "false"
2649 "ax = cases_m7.iloc[-50:][COUNTRIES_CORE].plot(figsize=(15, 9), title=\"Cases per day, 7 day moving average, with lockdown dates\") #, ylim=(-10, 1500))\n",
2650 "ax.set_xlabel(f\"Days since {DEATH_COUNT_THRESHOLD} deaths\")\n",
2651 "# uk_projection.deaths_m7.plot(ax=ax)\n",
2652 "for c in COUNTRIES_CORE:\n",
2653 " lvi = cases_m7[c].last_valid_index()\n",
2654 "# if c != 'UK':\n",
2655 " ax.text(x = lvi + 1, y = cases_m7[c][lvi], s = f\"{c}: {cases_m7[c][lvi]:.0f}\")\n"
2659 "cell_type": "code",
2660 "execution_count": null,
2662 "Collapsed": "false"
2666 "ax = cases_m7[COUNTRIES_CORE].plot(figsize=(15, 9), title=\"Cases per day, 7 day moving average, with lockdown dates\")\n",
2667 "ax.set_xlabel(f\"Days since {DEATH_COUNT_THRESHOLD} deaths\")\n",
2668 "# uk_projection.deaths_m7.plot(ax=ax)\n",
2669 "for c in COUNTRIES_CORE:\n",
2670 " lvi = cases_m7[c].last_valid_index()\n",
2671 "# if c != 'UK':\n",
2672 " ax.text(x = lvi + 1, y = cases_m7[c][lvi], s = f\"{c}: {cases_m7[c][lvi]:.0f}\")\n",
2673 " if c in lockdown_dates:\n",
2674 " for phase in lockdown_dates[c]:\n",
2675 " marker_col = [l for l in ax.lines if l.get_label() == c][0].get_color()\n",
2676 " if 'start' in phase:\n",
2677 " marker_shape = '^'\n",
2679 " marker_shape = 'v'\n",
2680 " ax.plot(lockdown_dates[c][phase]['since_threshold'], lockdown_dates[c][phase]['cases_m7'], \n",
2682 " markersize=18, markerfacecolor=marker_col, markeredgecolor=marker_col)\n",
2683 " if 'start' not in phase:\n",
2684 " ax.text(x = lockdown_dates[c][phase]['since_threshold'] + 1, y = lockdown_dates[c][phase]['cases_m7'], \n",
2685 " s = f\"{lockdown_dates[c][phase]['date']}: {lockdown_dates[c][phase]['cases_m7']:.0f}\")\n",
2686 "# plt.savefig('cases_per_day_with_lockdown.png')"
2690 "cell_type": "code",
2691 "execution_count": null,
2693 "Collapsed": "false"
2697 "plot_start_date = '2020-03-01'\n",
2698 "ax = cases_by_date_m7.loc[plot_start_date:, COUNTRIES_CORE].plot(figsize=(15, 9), title=\"Cases per day, 7 day moving average, with lockdown dates\")\n",
2699 "ax.set_xlabel(f\"Date\")\n",
2700 "ax.set_ylabel(\"Number of cases\")\n",
2701 "# uk_projection.deaths_m7.plot(ax=ax)\n",
2702 "for c in COUNTRIES_CORE:\n",
2703 " lvi = cases_by_date_m7[c].last_valid_index()\n",
2704 "# if c != 'UK':\n",
2705 " ax.text(x = lvi + pd.Timedelta(days=1), y = cases_by_date_m7[c][lvi], s = f\"{c}: {cases_by_date_m7[c][lvi]:.0f}\")\n",
2706 " if c in lockdown_dates:\n",
2707 " for phase in lockdown_dates[c]:\n",
2708 " marker_col = [l for l in ax.lines if l.get_label() == c][0].get_color()\n",
2709 " if 'start' in phase:\n",
2710 " marker_shape = '^'\n",
2712 " marker_shape = 'v'\n",
2713 " marker_x_pos = ax.get_xlim()[0] + mpl.dates.date2num(pd.to_datetime(lockdown_dates[c][phase]['date'])) - mpl.dates.date2num(pd.to_datetime(plot_start_date))\n",
2714 " ax.plot(marker_x_pos, lockdown_dates[c][phase]['cases_m7'], \n",
2716 " markersize=18, markerfacecolor=marker_col, markeredgecolor=marker_col)\n",
2717 " if 'start' not in phase:\n",
2718 " ax.text(x = marker_x_pos + 3, y = lockdown_dates[c][phase]['cases_m7'], \n",
2719 " s = f\"{lockdown_dates[c][phase]['date']}: {lockdown_dates[c][phase]['cases_m7']:.0f}\")\n",
2720 "plt.savefig('cases_per_day_with_lockdown.png')"
2724 "cell_type": "code",
2725 "execution_count": null,
2727 "Collapsed": "false"
2731 "ax = cases_m7[COUNTRIES_CORE].plot(figsize=(10, 6), title=\"Cases per day, 7 day moving average\")\n",
2732 "for c in COUNTRIES_CORE:\n",
2733 " lvi = cases_m7[c].last_valid_index()\n",
2734 " ax.text(x = lvi + 1, y = cases_m7[c][lvi], s = c)\n",
2735 "plt.savefig('covid_cases_per_day-core.png') "
2739 "cell_type": "code",
2740 "execution_count": null,
2742 "Collapsed": "false"
2746 "ax = deaths_m7[COUNTRIES_CORE].plot(figsize=(15, 9), title=\"Deaths per day, 7 day moving average\",\n",
2747 " xlim=(0, 15), \n",
2750 "# uk_projection.deaths_m7.plot(ax=ax)\n",
2751 "for c in COUNTRIES_CORE:\n",
2752 " lvi = deaths_m7[c].last_valid_index()\n",
2753 " if c in lockdown_dates:\n",
2754 " for phase in lockdown_dates[c]:\n",
2755 " if 'start' in phase:\n",
2756 " print(c, phase)\n",
2757 " marker_col = [l for l in ax.lines if l.get_label() == c][0].get_color()\n",
2758 " ax.plot(lockdown_dates[c][phase]['since_threshold'], lockdown_dates[c][phase]['deaths_m7'], '*', \n",
2759 " markersize=18, markerfacecolor=marker_col, markeredgecolor=marker_col)\n",
2760 " ax.text(x = lockdown_dates[c][phase]['since_threshold'] + 0.3, y = lockdown_dates[c][phase]['deaths_m7'], \n",
2761 " s = f\"{lockdown_dates[c][phase]['date']}: {lockdown_dates[c][phase]['deaths_m7']:.0f}\")\n",
2762 "# plt.savefig('school_reopenings.png')"
2766 "cell_type": "code",
2767 "execution_count": null,
2769 "Collapsed": "false"
2775 "cell_type": "code",
2776 "execution_count": null,
2778 "Collapsed": "false"
2784 "cell_type": "markdown",
2786 "Collapsed": "false"
2789 "# Write results to summary file"
2793 "cell_type": "code",
2794 "execution_count": null,
2796 "Collapsed": "false"
2800 "with open('covid_summary.md', 'w') as f:\n",
2801 " f.write('% Covid death data summary\\n')\n",
2802 " f.write('% Neil Smith\\n')\n",
2803 " f.write(f'% Created on {datetime.datetime.now().strftime(\"%Y-%m-%d\")}\\n')\n",
2804 " f.write('\\n')\n",
2806 " last_uk_date = data_since_threshold.replace([np.inf, -np.inf], np.nan).loc[(slice(None), ['UK']), 'dateRep'].iloc[-1]\n",
2807 " f.write(f'> Last UK data from {last_uk_date.strftime(\"%Y-%m-%d\")}\\n')\n",
2812 "cell_type": "code",
2813 "execution_count": null,
2815 "Collapsed": "false"
2819 "with open('covid_summary.md', 'a') as f:\n",
2820 " f.write('## Headlines\\n')\n",
2821 " f.write('\\n')\n",
2822 " f.write('| []() | |\\n')\n",
2823 " f.write('|:---|---:|\\n')\n",
2824 " f.write(f'| Deaths reported so far | {uk_covid_deaths} | \\n')\n",
2825 " f.write(f'| Total Covid deaths to date (estimated) | {uk_deaths_to_date:.0f} |\\n')\n",
2826 " projection_date = data_since_threshold.replace([np.inf, -np.inf], np.nan).loc[(slice(None), ['IT']), 'dateRep'].iloc[-1] + pd.Timedelta(s_end - s_start, unit='days')\n",
2827 "# f.write(f'| Projected total deaths up to {projection_date.strftime(\"%Y-%m-%d\")} | {deaths_actual_projected_scaled:.0f} | \\n')\n",
2832 "cell_type": "code",
2833 "execution_count": null,
2835 "Collapsed": "false"
2839 "with open('covid_summary.md', 'a') as f:\n",
2840 " f.write('## Total deaths\\n')\n",
2841 "# f.write(f'Time based on days since {DEATH_COUNT_THRESHOLD} deaths\\n')\n",
2842 " f.write('\\n')\n",
2843 " f.write('\\n')\n",
2844 " f.write('\\n')\n",
2845 " f.write('| Country ID | Country name | Total deaths |\\n')\n",
2846 " f.write('|:-----------|:-------------|-------------:|\\n')\n",
2847 " for c in sorted(COUNTRIES_CORE):\n",
2848 " lvi = deaths_by_date[c].last_valid_index()\n",
2849 " f.write(f'| {c} | {countries.loc[c].countriesAndTerritories} | {int(deaths_by_date[c][lvi])} |\\n')\n",
2854 "cell_type": "code",
2855 "execution_count": null,
2857 "Collapsed": "false"
2861 "with open('covid_summary.md', 'a') as f:\n",
2862 " f.write('## All-causes deaths, UK\\n')\n",
2863 " f.write('\\n')\n",
2864 " f.write('\\n')\n",
2865 " f.write('\\n')\n",
2866 " f.write('### True deaths\\n')\n",
2867 " f.write('\\n')\n",
2868 " f.write(f'The number of deaths reported in official statistics, {uk_covid_deaths}, is an underestimate '\n",
2869 " 'of the true number of Covid deaths.\\n'\n",
2870 " 'This is especially true early in the pandemic, approximately March to May 2020.\\n')\n",
2871 " f.write('We can get a better understanding of the impact of Covid by looking at the number of deaths, '\n",
2872 " 'over and above what would be expected at each week of the year.\\n')\n",
2873 " f.write(f'The ONS (and other bodies in Scotland and Northern Ireland) have released data on the number of deaths '\n",
2874 " f'up to {pd.to_datetime(excess_deaths_data[\"end_date\"]).strftime(\"%d %B %Y\")}.\\n\\n')\n",
2875 " f.write('If, for each of those weeks, I take the largest of the excess deaths or the reported Covid deaths, ')\n",
2876 " f.write(f'I estimate there have been **{uk_deaths_to_date}** total deaths so far.\\n')\n",
2881 "cell_type": "code",
2882 "execution_count": null,
2884 "Collapsed": "false"
2888 "# with open('covid_summary.md', 'a') as f:\n",
2889 "# f.write(f'In that period, the UK reported {ons_reported_deaths} Covid deaths.\\n')\n",
2890 "# f.write(f'In the last three weeks for which excess deaths have been reported, the excess deaths have been {excess_death_accuracy:.3f} higher than the Covid-reported deaths.\\n')\n",
2891 "# # f.write(f'That means the actual number of Covid death is about {excess_deaths / reported_deaths:.2f} times higher than the reported figures.\\n')\n",
2892 "# f.write('\\n')\n",
2893 "# f.write(f'The UK has reported {uk_covid_deaths} deaths so far.\\n')\n",
2894 "# f.write(f'Using the scaling factor above (for Covid-19 deaths after the ONS figures), I infer that there have been **{uk_deaths_to_date:.0f}** total deaths so far.\\n')\n",
2899 "cell_type": "code",
2900 "execution_count": null,
2902 "Collapsed": "false"
2906 "with open('covid_summary.md', 'a') as f:\n",
2907 " f.write('## Deaths per day\\n')\n",
2908 " f.write(f'Based on a 7-day moving average\\n')\n",
2909 " f.write('\\n')\n",
2910 " f.write('\\n')\n",
2911 " f.write('\\n')\n",
2912 " f.write('\\n')\n",
2917 "cell_type": "code",
2918 "execution_count": null,
2920 "Collapsed": "false"
2924 "s_end - s_start - 1"
2928 "cell_type": "code",
2929 "execution_count": null,
2931 "Collapsed": "false"
2935 "with open('covid_summary.md', 'a') as f:\n",
2936 " f.write('## Projected deaths\\n')\n",
2937 " f.write(\"Previously, I was using Italy's deaths data to predict the UK's deaths data. \"\n",
2938 " \"This worked when both countries' trends of deaths were falling or constant, \"\n",
2939 " \"as they were until September.\\n\")\n",
2940 " f.write(\"\\n\")\n",
2941 " f.write(\"As of mid-September, with cases rising in both countries at around the same time, \"\n",
2942 " \"I can't use Italian data to predict the UK's future deaths.\\n\")\n",
2943 " f.write(\"\\n\")\n",
2944 "# f.write(f\"The UK's daily deaths data is very similar to Italy's.\\n\")\n",
2945 "# f.write(f'If I use the Italian data for the next {s_end - s_start - 1} days (from {s_start_date.strftime(\"%d %B %Y\")} onwards),')\n",
2946 "# f.write(f' the UK will report {uk_projection.deaths.sum()} deaths on day {uk_end} of the epidemic.\\n')\n",
2947 "# f.write('\\n')\n",
2948 "# f.write('Using the excess deaths scaling from above, that will translate into ')\n",
2949 "# f.write(f'**{deaths_actual_projected_scaled:.0f}** Covid deaths total.\\n')\n",
2954 "cell_type": "code",
2955 "execution_count": null,
2957 "Collapsed": "false"
2961 "with open('covid_summary.md', 'a') as f:\n",
2962 " f.write('## Deaths doubling times\\n')\n",
2963 " f.write(f'Based on a 7-day moving average\\n')\n",
2964 " f.write('\\n')\n",
2965 " f.write('\\n')\n",
2970 "cell_type": "code",
2971 "execution_count": null,
2973 "Collapsed": "false"
2977 "with open('covid_summary.md', 'a') as f:\n",
2978 " f.write('\\n')\n",
2979 " f.write('## Cases per day and lockdown dates\\n')\n",
2980 " f.write(f'Based on a 7-day moving average\\n')\n",
2981 " f.write('\\n')\n",
2982 " f.write('\\n')\n",
2987 "cell_type": "code",
2988 "execution_count": null,
2990 "Collapsed": "false"
2994 "with open('covid_summary.md', 'a') as f:\n",
2995 " f.write('| Country ID | Country name | Most recent daily cases | Most recent daily deaths |\\n')\n",
2996 " f.write('|:-----------|:-------------|------------------------:|-------------------------:|\\n')\n",
2997 " for c in sorted(COUNTRIES_CORE):\n",
2998 " lvic = cases_m7[c].last_valid_index()\n",
2999 " lvid = deaths_m7[c].last_valid_index()\n",
3000 " f.write(f'| {c} | {countries.loc[c].countriesAndTerritories} | {cases_m7[c][lvic]:.0f} | {deaths_m7[c][lvid]:.0f} | \\n')\n",
3001 " f.write('\\n')\n",
3002 " f.write('(Figures are 7-day averages)\\n')\n",
3007 "cell_type": "code",
3008 "execution_count": null,
3010 "Collapsed": "false"
3014 "with open('hospital_normalisation_date.json') as f:\n",
3015 " hospital_normalisation_date_data = json.load(f)"
3019 "cell_type": "code",
3020 "execution_count": null,
3022 "Collapsed": "false"
3026 "with open('covid_summary.md', 'a') as f:\n",
3027 " f.write('## Hospital care\\n')\n",
3028 " f.write(f'Based on a 7-day moving average\\n')\n",
3029 " f.write('\\n')\n",
3030 " f.write('\\n')\n",
3031 " f.write('\\n')\n",
3032 "# f.write('Admissions are shifted by 10 days, deaths by 25 days. '\n",
3033 "# 'This reflects the typical timescales of infection: '\n",
3034 "# 'patients are admitted 10 days after onset of symptoms, '\n",
3035 "# 'and die 15 days after admission.\\n')\n",
3036 "# f.write('\\n')\n",
3037 "# f.write('Plotting this data with offsets shows more clearly '\n",
3038 "# 'the relative changes in these three metrics.\\n')\n",
3039 " f.write('Due to the large scale differences between the three '\n",
3040 " 'measures, they are all normalised to show changes ')\n",
3041 " f.write(f'since {pd.to_datetime(hospital_normalisation_date_data[\"hospital_normalisation_date\"]).strftime(\"%d %B %Y\")}.\\n')\n",
3046 "cell_type": "code",
3047 "execution_count": null,
3049 "Collapsed": "false"
3053 "with open('covid_summary.md', 'a') as f:\n",
3054 " f.write('## Testing effectiveness\\n')\n",
3055 " f.write('\\n')\n",
3056 " f.write('A question about testing is whether more detected cases is a result of more tests being '\n",
3057 " 'done or is because the number of cases is increasing. One way of telling the differeence '\n",
3058 " 'is by looking at the fraction of tests that are positive.\\n')\n",
3059 " f.write('\\n')\n",
3060 " f.write('\\n')\n",
3061 " f.write('\\n')\n",
3062 " f.write('Numbers of positive tests and cases, '\n",
3063 " '7-day moving average.\\n'\n",
3064 " 'Note the different y-axes\\n')\n",
3065 " f.write('\\n') \n",
3066 " f.write('\\n')\n",
3067 " f.write('\\n')\n",
3068 " f.write('Fraction of tests with a positive result, both daily figures and '\n",
3069 " '7-day moving average.\\n')\n",
3070 " f.write('\\n') \n",
3071 " f.write('\\n')\n",
3072 " f.write('\\n')\n",
3073 " f.write('\\n')\n",
3074 " f.write('The trajectory of tests done vs fraction positive tests.\\n')\n",
3075 " f.write('\\n')\n",
3076 " f.write('Points higher indicate more tests; points to the right indicate more positive tests.'\n",
3077 " 'More tests being done with the same infection prevelance will move the point up '\n",
3078 " 'and to the left.\\n')\n",
3079 " f.write('\\n')\n",
3080 " f.write('\\n')\n",
3081 " f.write('\\n')\n",
3086 "cell_type": "code",
3087 "execution_count": null,
3089 "Collapsed": "false"
3095 "cell_type": "code",
3096 "execution_count": null,
3098 "Collapsed": "false"
3102 "with open('covid_summary.md', 'a') as f:\n",
3103 " f.write('# Data sources\\n')\n",
3104 " f.write('\\n')\n",
3105 " f.write('> Covid data from [European Centre for Disease Prevention and Control](https://www.ecdc.europa.eu/en/publications-data/download-todays-data-geographic-distribution-covid-19-cases-worldwide)\\n')\n",
3106 " f.write('\\n') \n",
3107 " f.write(\"\"\"> Population data from:\n",
3109 "* [Office of National Statistics](https://www.ons.gov.uk/peoplepopulationandcommunity/birthsdeathsandmarriages/deaths/datasets/weeklyprovisionalfiguresondeathsregisteredinenglandandwales) (Endland and Wales) Weeks start on a Saturday.\n",
3110 "* [Northern Ireland Statistics and Research Agency](https://www.nisra.gov.uk/publications/weekly-deaths) (Northern Ireland). Weeks start on a Saturday. Note that the week numbers don't match the England and Wales data.\n",
3111 "* [National Records of Scotland](https://www.nrscotland.gov.uk/statistics-and-data/statistics/statistics-by-theme/vital-events/general-publications/weekly-and-monthly-data-on-births-and-deaths/weekly-data-on-births-and-deaths) (Scotland). Note that Scotland uses ISO8601 week numbers, which start on a Monday.\"\"\")\n",
3113 " f.write('\\n\\n')\n",
3114 " f.write('> [Source code available](https://git.njae.me.uk/?p=covid19.git;a=tree)\\n')\n",
3115 " f.write('\\n') \n"
3119 "cell_type": "code",
3120 "execution_count": null,
3122 "Collapsed": "false"
3126 "!pandoc --toc -s covid_summary.md > covid_summary.html"
3130 "cell_type": "code",
3131 "execution_count": null,
3133 "Collapsed": "false"
3137 "!scp covid_summary.html neil@ogedei:/var/www/scripts.njae.me.uk/covid/index.html\n",
3138 "!scp covid_deaths_total_linear.png neil@ogedei:/var/www/scripts.njae.me.uk/covid/\n",
3139 "!scp deaths-radar.png neil@ogedei:/var/www/scripts.njae.me.uk/covid/\n",
3140 "!scp covid_deaths_per_day_7.png neil@ogedei:/var/www/scripts.njae.me.uk/covid/\n",
3141 "!scp covid_doubling_times_7.png neil@ogedei:/var/www/scripts.njae.me.uk/covid/\n",
3142 "!scp cases_per_day_with_lockdown.png neil@ogedei:/var/www/scripts.njae.me.uk/covid/\n",
3143 "!scp cases_admissions_deaths.png neil@ogedei:/var/www/scripts.njae.me.uk/covid/\n",
3144 "!scp fraction_positive_tests.png neil@ogedei:/var/www/scripts.njae.me.uk/covid/ \n",
3145 "!scp tests_and_cases.png neil@ogedei:/var/www/scripts.njae.me.uk/covid/\n",
3146 "!scp deaths_by_date_last_30_days.png neil@ogedei:/var/www/scripts.njae.me.uk/covid/\n",
3147 "!scp fraction_positive_tests_vs_tests.png neil@ogedei:/var/www/scripts.njae.me.uk/covid/\n",
3148 "!scp tests_vs_fraction_positive_animation.png neil@ogedei:/var/www/scripts.njae.me.uk/covid/ "
3152 "cell_type": "code",
3153 "execution_count": null,
3155 "Collapsed": "false"
3159 "with open('uk_covid_deaths.js', 'w') as f:\n",
3160 " f.write(f\"document.write('{uk_covid_deaths}');\")\n",
3162 "with open('estimated_total_deaths.js', 'w') as f:\n",
3163 " f.write(f\"document.write('{uk_deaths_to_date:.0f}');\")\n",
3165 "# with open('projection_date.js', 'w') as f:\n",
3166 "# f.write(f\"document.write(\\'{projection_date.strftime('%d %B %Y')}\\');\")\n",
3168 "# with open('projected_deaths.js', 'w') as f:\n",
3169 "# f.write(f\"document.write('{uk_projection.deaths.sum():.0f}');\")\n",
3171 "# with open('projected_excess_deaths.js', 'w') as f:\n",
3172 "# f.write(f\"document.write('{deaths_actual_projected_scaled:.0f}');\")\n",
3174 "edut = pd.to_datetime(excess_deaths_data[\"end_date\"]).strftime('%d %B %Y')\n",
3175 "with open('excess_deaths_upto.js', 'w') as f:\n",
3176 " f.write(f\"document.write('{edut}');\")\n",
3178 "# with open('excess_deaths.js', 'w') as f:\n",
3179 "# f.write(f\"document.write('{excess_deaths:.0f}');\")\n",
3181 "# with open('reported_deaths.js', 'w') as f:\n",
3182 "# f.write(f\"document.write('{ons_reported_deaths:.0f}');\")\n",
3184 "# with open('scaling_factor.js', 'w') as f:\n",
3185 "# f.write(f\"document.write('{excess_death_accuracy:.2f}');\") \n",
3187 "# with open('projection_length.js', 'w') as f:\n",
3188 "# f.write(f\"document.write('{s_end - s_start - 1}');\")\n",
3190 "# with open('s_end.js', 'w') as f:\n",
3191 "# f.write(f\"document.write('{s_end}');\")\n",
3193 "# s_start_date_str = s_start_date.strftime(\"%d %B %Y\")\n",
3194 "# with open('s_start_date.js', 'w') as f:\n",
3195 "# f.write(f\"document.write('{s_start_date_str}');\")\n",
3197 "# with open('uk_end.js', 'w') as f:\n",
3198 "# f.write(f\"document.write('{uk_end}');\")\n",
3200 "with open('last_uk_date.js', 'w') as f:\n",
3201 " f.write(f\"document.write('{pd.to_datetime(last_uk_date).strftime('%d %B %Y')}');\")"
3205 "cell_type": "code",
3206 "execution_count": null,
3208 "Collapsed": "false"
3212 "# pd.to_datetime(excess_deaths_upto).strftime('%d %B %Y')"
3216 "cell_type": "code",
3217 "execution_count": null,
3219 "Collapsed": "false"
3223 "!scp uk_covid_deaths.js neil@ogedei:/var/www/scripts.njae.me.uk/covid/\n",
3224 "!scp estimated_total_deaths.js neil@ogedei:/var/www/scripts.njae.me.uk/covid/\n",
3225 "# !scp projection_date.js neil@ogedei:/var/www/scripts.njae.me.uk/covid/\n",
3226 "# !scp projected_deaths.js neil@ogedei:/var/www/scripts.njae.me.uk/covid/\n",
3227 "# !scp projected_excess_deaths.js neil@ogedei:/var/www/scripts.njae.me.uk/covid/\n",
3228 "!scp excess_deaths_upto.js neil@ogedei:/var/www/scripts.njae.me.uk/covid/\n",
3229 "# !scp excess_deaths.js neil@ogedei:/var/www/scripts.njae.me.uk/covid/\n",
3230 "# !scp reported_deaths.js neil@ogedei:/var/www/scripts.njae.me.uk/covid/\n",
3231 "# !scp scaling_factor.js neil@ogedei:/var/www/scripts.njae.me.uk/covid/\n",
3232 "# !scp projection_length.js neil@ogedei:/var/www/scripts.njae.me.uk/covid/\n",
3233 "# !scp s_end.js neil@ogedei:/var/www/scripts.njae.me.uk/covid/\n",
3234 "# !scp s_start_date.js neil@ogedei:/var/www/scripts.njae.me.uk/covid/\n",
3235 "# !scp uk_end.js neil@ogedei:/var/www/scripts.njae.me.uk/covid/\n",
3236 "!scp last_uk_date.js neil@ogedei:/var/www/scripts.njae.me.uk/covid/\n",
3237 "!scp hospital_normalisation_date.js neil@ogedei:/var/www/scripts.njae.me.uk/covid/"
3241 "cell_type": "code",
3242 "execution_count": null,
3244 "Collapsed": "false"
3248 "data_by_date.loc['UK'].to_csv('data_by_day_uk.csv', header=True, index=True)\n",
3249 "data_by_date.loc['BE'].to_csv('data_by_day_be.csv', header=True, index=True)"
3253 "cell_type": "code",
3254 "execution_count": null,
3256 "Collapsed": "false"
3260 "ukd = data_since_threshold.replace([np.inf, -np.inf], np.nan).loc[(slice(None), ['UK']), ['deaths', 'deaths_m7']].droplevel(1)\n",
3261 "ax = ukd.deaths.plot.bar(figsize=(12, 8))\n",
3262 "ukd.deaths_m7.plot.line(ax=ax, color='red')\n",
3263 "# ax = data_since_threshold.replace([np.inf, -np.inf], np.nan).loc[(slice(None), ['UK']), 'deaths_m7'].plot.line(figsize=(12, 8), color='red')\n",
3264 "# ax = data_since_threshold.replace([np.inf, -np.inf], np.nan).loc[(slice(None), ['UK']), 'deaths'].plot.bar(ax=ax)\n",
3265 "ax.set_xticks(range(0, 120, 20))"
3269 "cell_type": "code",
3270 "execution_count": null,
3272 "Collapsed": "false"
3276 "ukdd = data_by_date.loc['UK'].iloc[-30:]\n",
3277 "ax = ukdd.deaths_m7.plot.line(figsize=(12, 8), color='red')\n",
3278 "# ukdd.deaths.plot.bar(ax=ax)\n",
3279 "ax.bar(ukdd.index, ukdd.deaths)"
3283 "cell_type": "code",
3284 "execution_count": null,
3286 "Collapsed": "false"
3294 "cell_type": "code",
3295 "execution_count": null,
3297 "Collapsed": "false"
3301 "np.arange(0, 130, 20)"
3305 "cell_type": "code",
3306 "execution_count": null,
3308 "Collapsed": "false"
3312 "data_by_date.loc['UK']"
3316 "cell_type": "code",
3317 "execution_count": null,
3319 "Collapsed": "false"
3323 "data_by_date.loc['UK'].plot(x='deaths_culm', y='deaths', logx=True, logy=True)"
3327 "cell_type": "code",
3328 "execution_count": null,
3330 "Collapsed": "false"
3334 "data_by_date.loc['UK'].plot(x='cases_culm', y='cases')"
3338 "cell_type": "code",
3339 "execution_count": null,
3341 "Collapsed": "false"
3345 "ukdbd = data_by_date.loc['UK'].copy()\n",
3346 "ukdbd['deaths_m7'] = ukdbd.deaths.transform(lambda x: x.rolling(7, 1).mean())\n",
3347 "ukdbd['cases_m7'] = ukdbd.cases.transform(lambda x: x.rolling(7, 1).mean())\n",
3352 "cell_type": "code",
3353 "execution_count": null,
3355 "Collapsed": "false"
3359 "ukdbd.plot(x='deaths_culm', y='deaths_m7', logx=True, logy=True)"
3363 "cell_type": "code",
3364 "execution_count": null,
3366 "Collapsed": "false"
3370 "fig, ax = plt.subplots(figsize=(12, 8))\n",
3372 "for c in COUNTRIES_CORE:\n",
3373 " if data_since_threshold.loc[(slice(None), c), 'deaths_culm'].max() > xmax:\n",
3374 " xmax = data_since_threshold.loc[(slice(None), c), 'deaths_culm'].max()\n",
3375 " data_since_threshold.loc[(slice(None), c), :].plot(x='deaths_culm', y='deaths_m7', logx=True, logy=True, xlim=(10, xmax * 1.1), label=c, ax=ax)"
3379 "cell_type": "code",
3380 "execution_count": null,
3382 "Collapsed": "false"
3386 "data_since_threshold.loc[(slice(None), 'UK'), 'deaths_culm'].max()"
3390 "cell_type": "code",
3391 "execution_count": null,
3393 "Collapsed": "false"
3397 "countries.continentExp.unique()"
3401 "cell_type": "code",
3402 "execution_count": null,
3404 "Collapsed": "false"
3408 "countries.loc['KW']"
3412 "cell_type": "code",
3413 "execution_count": null,
3415 "Collapsed": "false"
3419 "data_by_date.groupby(level=0)['deaths'].shift(-25)"
3423 "cell_type": "code",
3424 "execution_count": null,
3426 "Collapsed": "false"
3430 "offset_data = data_by_date.loc[:, ['cases']]\n",
3431 "offset_data['deaths'] = data_by_date.groupby(level=0)['deaths'].shift(-25)\n",
3432 "offset_data['cases_m7'] = offset_data.groupby(level=0)['cases'].transform(lambda x: x.rolling(7, 1).mean())\n",
3433 "offset_data['deaths_m7'] = offset_data['deaths'].dropna().groupby(level=0).transform(lambda x: x.rolling(7, 1).mean())\n",
3434 "offset_data['deaths_per_case'] = offset_data.deaths_m7 / offset_data.cases_m7\n",
3439 "cell_type": "code",
3440 "execution_count": null,
3442 "Collapsed": "false"
3450 "cell_type": "code",
3451 "execution_count": null,
3453 "Collapsed": "false"
3457 "offset_deaths_m7 = (offset_data.loc[COUNTRIES_ALL, ['deaths_m7']]\n",
3458 " .unstack().sort_index().xs('deaths_m7', axis=1, drop_level=True)).T.sort_index()\n",
3463 "cell_type": "code",
3464 "execution_count": null,
3466 "Collapsed": "false"
3470 "offset_deaths_m7['UK']"
3474 "cell_type": "code",
3475 "execution_count": null,
3477 "Collapsed": "false"
3481 "data_since_threshold.loc[(slice(None), 'UK'), :].tail()"
3485 "cell_type": "code",
3486 "execution_count": null,
3488 "Collapsed": "false"
3492 "countries.loc['PT']"
3496 "cell_type": "code",
3497 "execution_count": null,
3499 "Collapsed": "false"
3503 "ax = cases_by_date_m7.iloc[-50:][COUNTRIES_FRIENDS].plot(figsize=(15, 9), title=\"Cases per day, 7 day moving average\")#, ylim=(-10, 1500))\n",
3504 "# ax.set_xlabel(f\"Days since {DEATH_COUNT_THRESHOLD} deaths\")\n",
3505 "# uk_projection.deaths_m7.plot(ax=ax)\n",
3506 "for c in COUNTRIES_FRIENDS:\n",
3507 " lvi = cases_by_date_m7[c].last_valid_index()\n",
3508 " ax.text(x = lvi + pd.Timedelta(days=1), y = cases_by_date_m7[c][lvi], s = f\"{c}: {cases_by_date_m7[c][lvi]:.0f}\")\n"
3512 "cell_type": "code",
3513 "execution_count": null,
3515 "Collapsed": "false"
3519 "ax = deaths_by_date_m7.iloc[-50:][COUNTRIES_FRIENDS].plot(figsize=(15, 9), title=\"Deaths per day, 7 day moving average\")#, ylim=(-10, 100))\n",
3520 "# ax.set_xlabel(f\"Days since {DEATH_COUNT_THRESHOLD} deaths\")\n",
3521 "# uk_projection.deaths_m7.plot(ax=ax)\n",
3522 "for c in COUNTRIES_FRIENDS:\n",
3523 " lvi = deaths_by_date_m7[c].last_valid_index()\n",
3524 "# if c != 'ES':\n",
3525 " ax.text(x = lvi + pd.Timedelta(days=1), y = deaths_by_date_m7[c][lvi], s = f\"{c}: {deaths_by_date_m7[c][lvi]:.0f}\")"
3529 "cell_type": "code",
3530 "execution_count": null,
3532 "Collapsed": "false"
3540 "formats": "ipynb,md"
3543 "display_name": "Python 3",
3544 "language": "python",
3548 "codemirror_mode": {
3552 "file_extension": ".py",
3553 "mimetype": "text/x-python",
3555 "nbconvert_exporter": "python",
3556 "pygments_lexer": "ipython3",