{ "cells": [ { "cell_type": "markdown", "id": "sticky-exhibit", "metadata": {}, "source": [ "# Demo\n", "\n", "Author: Cindy Chiao\n", "Last Modified: Nov 16, 2021\n", "\n", "## What is xbatcher? \n", "Xbatcher is a small library for iterating through xarray objects (DataArrays and Datasets) in batches. The goal is to make it easy to feed xarray objects to machine learning libraries such as Keras and PyTorch. \n", "\n", "## What is included in this notebook?\n", "* showcase current abilities with example data \n", "* brief discussion of current development track and ideas for future work " ] }, { "cell_type": "code", "execution_count": 1, "id": "banner-importance", "metadata": {}, "outputs": [], "source": [ "import xarray as xr\n", "import xbatcher\n", "import fsspec" ] }, { "cell_type": "markdown", "id": "equipped-sense", "metadata": {}, "source": [ "## Example data\n", "\n", "Here we will load an example dataset from a global climate model. The data is from the _historical_ experiment from CMIP6 and represents 60 days of daily max air temperature. " ] }, { "cell_type": "code", "execution_count": 2, "id": "dutch-grave", "metadata": {}, "outputs": [ { "data": { "text/html": [ "
\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "
<xarray.Dataset>\n",
       "Dimensions:  (lat: 145, lon: 192, time: 60)\n",
       "Coordinates:\n",
       "  * lat      (lat) float64 -90.0 -88.75 -87.5 -86.25 ... 86.25 87.5 88.75 90.0\n",
       "  * lon      (lon) float64 0.0 1.875 3.75 5.625 7.5 ... 352.5 354.4 356.2 358.1\n",
       "  * time     (time) datetime64[ns] 1850-01-01T12:00:00 ... 1850-03-01T12:00:00\n",
       "Data variables:\n",
       "    tasmax   (time, lat, lon) float32 dask.array<chunksize=(60, 145, 192), meta=np.ndarray>
" ], "text/plain": [ "\n", "Dimensions: (lat: 145, lon: 192, time: 60)\n", "Coordinates:\n", " * lat (lat) float64 -90.0 -88.75 -87.5 -86.25 ... 86.25 87.5 88.75 90.0\n", " * lon (lon) float64 0.0 1.875 3.75 5.625 7.5 ... 352.5 354.4 356.2 358.1\n", " * time (time) datetime64[ns] 1850-01-01T12:00:00 ... 1850-03-01T12:00:00\n", "Data variables:\n", " tasmax (time, lat, lon) float32 dask.array" ] }, "metadata": {}, "output_type": "display_data" } ], "source": [ "store = fsspec.get_mapper(\n", " \"az://carbonplan-share/example_cmip6_data.zarr\", account_name=\"carbonplan\"\n", ")\n", "ds = xr.open_zarr(store, consolidated=True)\n", "\n", "# the attributes contain a lot of useful information, but clutter the print out when we inspect the outputs\n", "# throughout this demo, clearing it to avoid confusion\n", "ds.attrs = {}\n", "\n", "# inspect the dataset\n", "display(ds)" ] }, { "cell_type": "code", "execution_count": 3, "id": "applicable-diesel", "metadata": {}, "outputs": [ { "data": { "text/plain": [ "" ] }, "execution_count": 3, "metadata": {}, "output_type": "execute_result" }, { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "# plot the first time dimension\n", "ds.isel(time=0).tasmax.plot()" ] }, { "cell_type": "markdown", "id": "animated-marsh", "metadata": {}, "source": [ "## Batch generation\n", "\n", "Xbatcher's `BatchGenerator` can be used to generate batches with several arguments controlling the exact behavior.\n", "\n", "The `input_dims` argument takes a dictionary specifying the size of the inputs in each dimension. For example, `{'time': 10}` means that each of the input sample will have 10 time points, while all other dimensions are flattened to a \"sample\" dimension\n", "\n", "Note that even though `ds` in this case only has one variable, the function can operate on multiple variables at the same time." ] }, { "cell_type": "code", "execution_count": 4, "id": "attempted-cooling", "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "6 batches\n" ] }, { "data": { "text/html": [ "
\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "
<xarray.Dataset>\n",
       "Dimensions:  (sample: 27840, time: 10)\n",
       "Coordinates:\n",
       "  * time     (time) datetime64[ns] 1850-02-20T12:00:00 ... 1850-03-01T12:00:00\n",
       "  * sample   (sample) MultiIndex\n",
       "  - lat      (sample) float64 -90.0 -90.0 -90.0 -90.0 ... 90.0 90.0 90.0 90.0\n",
       "  - lon      (sample) float64 0.0 1.875 3.75 5.625 ... 352.5 354.4 356.2 358.1\n",
       "Data variables:\n",
       "    tasmax   (sample, time) float32 226.1 226.2 224.0 ... 251.5 245.5 242.9
" ], "text/plain": [ "\n", "Dimensions: (sample: 27840, time: 10)\n", "Coordinates:\n", " * time (time) datetime64[ns] 1850-02-20T12:00:00 ... 1850-03-01T12:00:00\n", " * sample (sample) MultiIndex\n", " - lat (sample) float64 -90.0 -90.0 -90.0 -90.0 ... 90.0 90.0 90.0 90.0\n", " - lon (sample) float64 0.0 1.875 3.75 5.625 ... 352.5 354.4 356.2 358.1\n", "Data variables:\n", " tasmax (sample, time) float32 226.1 226.2 224.0 ... 251.5 245.5 242.9" ] }, "metadata": {}, "output_type": "display_data" } ], "source": [ "n_timepoint_in_each_sample = 10\n", "\n", "bgen = xbatcher.BatchGenerator(\n", " ds=ds,\n", " input_dims={\"time\": n_timepoint_in_each_sample},\n", ")\n", "\n", "n_batch = 0\n", "for batch in bgen:\n", " n_batch += 1\n", "\n", "print(f\"{n_batch} batches\")\n", "display(batch)" ] }, { "cell_type": "markdown", "id": "digital-night", "metadata": {}, "source": [ "We can verify that the outputs have the expected shapes. \n", "\n", "For example, there are 60 time points in our input dataset, we're asking 10 timepoints in each batch, thus expecting 6 batches " ] }, { "cell_type": "code", "execution_count": 5, "id": "integral-theta", "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "Expecting 6.0 batches, getting 6 batches\n" ] } ], "source": [ "expected_n_batch = len(ds.time) / n_timepoint_in_each_sample\n", "print(f\"Expecting {expected_n_batch} batches, getting {n_batch} batches\")" ] }, { "cell_type": "markdown", "id": "usual-kennedy", "metadata": {}, "source": [ "There are 145 lat points and 192 lon points, thus we're expecting 145 * 192 = 27840 samples in a batch." ] }, { "cell_type": "code", "execution_count": 6, "id": "incomplete-native", "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "Expecting 27840 samples per batch, getting 27840 samples per batch\n" ] } ], "source": [ "expected_batch_size = len(ds.lat) * len(ds.lon)\n", "print(\n", " f\"Expecting {expected_batch_size} samples per batch, getting {len(batch.sample)} samples per batch\"\n", ")" ] }, { "cell_type": "markdown", "id": "durable-gazette", "metadata": {}, "source": [ "## Controlling the size/shape of batches\n", "\n", "We can use `batch_dims` and `concat_input_dims` options to control how many sample ends up in each batch. For example, we can specify 10 time points for each sample, but 20 time points in each batch this should yield half as many batches and twice as many samples in a batch as the example above note the difference in dimension name in this case " ] }, { "cell_type": "code", "execution_count": 7, "id": "sophisticated-legislation", "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "3 batches\n" ] }, { "data": { "text/html": [ "
\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "
<xarray.Dataset>\n",
       "Dimensions:      (sample: 55680, time_input: 10)\n",
       "Coordinates:\n",
       "    time         (sample, time_input) datetime64[ns] 1850-02-10T12:00:00 ... ...\n",
       "  * sample       (sample) MultiIndex\n",
       "  - input_batch  (sample) int64 0 0 0 0 0 0 0 0 0 0 0 ... 1 1 1 1 1 1 1 1 1 1 1\n",
       "  - lat          (sample) float64 -90.0 -90.0 -90.0 -90.0 ... 90.0 90.0 90.0\n",
       "  - lon          (sample) float64 0.0 1.875 3.75 5.625 ... 354.4 356.2 358.1\n",
       "Dimensions without coordinates: time_input\n",
       "Data variables:\n",
       "    tasmax       (sample, time_input) float32 238.8 235.2 234.7 ... 245.5 242.9
" ], "text/plain": [ "\n", "Dimensions: (sample: 55680, time_input: 10)\n", "Coordinates:\n", " time (sample, time_input) datetime64[ns] 1850-02-10T12:00:00 ... ...\n", " * sample (sample) MultiIndex\n", " - input_batch (sample) int64 0 0 0 0 0 0 0 0 0 0 0 ... 1 1 1 1 1 1 1 1 1 1 1\n", " - lat (sample) float64 -90.0 -90.0 -90.0 -90.0 ... 90.0 90.0 90.0\n", " - lon (sample) float64 0.0 1.875 3.75 5.625 ... 354.4 356.2 358.1\n", "Dimensions without coordinates: time_input\n", "Data variables:\n", " tasmax (sample, time_input) float32 238.8 235.2 234.7 ... 245.5 242.9" ] }, "metadata": {}, "output_type": "display_data" } ], "source": [ "n_timepoint_in_each_sample = 10\n", "n_timepoint_in_each_batch = 20\n", "\n", "bgen = xbatcher.BatchGenerator(\n", " ds=ds,\n", " input_dims={\"time\": n_timepoint_in_each_sample},\n", " batch_dims={\"time\": n_timepoint_in_each_batch},\n", " concat_input_dims=True,\n", ")\n", "\n", "n_batch = 0\n", "for batch in bgen:\n", " n_batch += 1\n", "\n", "print(f\"{n_batch} batches\")\n", "display(batch)" ] }, { "cell_type": "markdown", "id": "spectacular-reading", "metadata": {}, "source": [ "## Last batch behavior\n", "\n", "If the input ds is not divisible by the specified `input_dims`, the remainder will be discarded instead of having a fractional batch. See https://github.com/xarray-contrib/xbatcher/issues/5 for more on this topic." ] }, { "cell_type": "code", "execution_count": 8, "id": "residential-income", "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "last time point in ds is 1850-03-01T12:00:00.000000000\n", "last time point in batch is 1850-01-31T12:00:00.000000000\n" ] }, { "data": { "text/html": [ "
\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "
<xarray.Dataset>\n",
       "Dimensions:  (sample: 27840, time: 31)\n",
       "Coordinates:\n",
       "  * time     (time) datetime64[ns] 1850-01-01T12:00:00 ... 1850-01-31T12:00:00\n",
       "  * sample   (sample) MultiIndex\n",
       "  - lat      (sample) float64 -90.0 -90.0 -90.0 -90.0 ... 90.0 90.0 90.0 90.0\n",
       "  - lon      (sample) float64 0.0 1.875 3.75 5.625 ... 352.5 354.4 356.2 358.1\n",
       "Data variables:\n",
       "    tasmax   (sample, time) float32 252.6 250.9 250.4 ... 257.6 256.9 243.3
" ], "text/plain": [ "\n", "Dimensions: (sample: 27840, time: 31)\n", "Coordinates:\n", " * time (time) datetime64[ns] 1850-01-01T12:00:00 ... 1850-01-31T12:00:00\n", " * sample (sample) MultiIndex\n", " - lat (sample) float64 -90.0 -90.0 -90.0 -90.0 ... 90.0 90.0 90.0 90.0\n", " - lon (sample) float64 0.0 1.875 3.75 5.625 ... 352.5 354.4 356.2 358.1\n", "Data variables:\n", " tasmax (sample, time) float32 252.6 250.9 250.4 ... 257.6 256.9 243.3" ] }, "metadata": {}, "output_type": "display_data" } ], "source": [ "n_timepoint_in_batch = 31\n", "\n", "bgen = xbatcher.BatchGenerator(ds=ds, input_dims={\"time\": n_timepoint_in_batch})\n", "\n", "for batch in bgen:\n", " print(f\"last time point in ds is {ds.time[-1].values}\")\n", " print(f\"last time point in batch is {batch.time[-1].values}\")\n", "display(batch)" ] }, { "cell_type": "markdown", "id": "competitive-islam", "metadata": {}, "source": [ "## Overlapping inputs\n", "\n", "In the example above, all samples have distinct time points. That is, for any lat/lon pixel, sample 1 has time points 1-10, sample 2 has time point 11-20, and they do not overlap \n", "however, in many machine learning applications, we will want overlapping samples (e.g. sample 1 has time points 1-10, sample 2 has time points 2-11, and so on). We can use the `input_overlap` argument to get this behavior." ] }, { "cell_type": "code", "execution_count": 9, "id": "cleared-custody", "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "3 batches\n" ] }, { "data": { "text/html": [ "
\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "
<xarray.Dataset>\n",
       "Dimensions:      (sample: 306240, time_input: 10)\n",
       "Coordinates:\n",
       "    time         (sample, time_input) datetime64[ns] 1850-02-10T12:00:00 ... ...\n",
       "  * sample       (sample) MultiIndex\n",
       "  - input_batch  (sample) int64 0 0 0 0 0 0 0 0 0 ... 10 10 10 10 10 10 10 10 10\n",
       "  - lat          (sample) float64 -90.0 -90.0 -90.0 -90.0 ... 90.0 90.0 90.0\n",
       "  - lon          (sample) float64 0.0 1.875 3.75 5.625 ... 354.4 356.2 358.1\n",
       "Dimensions without coordinates: time_input\n",
       "Data variables:\n",
       "    tasmax       (sample, time_input) float32 238.8 235.2 234.7 ... 245.5 242.9
" ], "text/plain": [ "\n", "Dimensions: (sample: 306240, time_input: 10)\n", "Coordinates:\n", " time (sample, time_input) datetime64[ns] 1850-02-10T12:00:00 ... ...\n", " * sample (sample) MultiIndex\n", " - input_batch (sample) int64 0 0 0 0 0 0 0 0 0 ... 10 10 10 10 10 10 10 10 10\n", " - lat (sample) float64 -90.0 -90.0 -90.0 -90.0 ... 90.0 90.0 90.0\n", " - lon (sample) float64 0.0 1.875 3.75 5.625 ... 354.4 356.2 358.1\n", "Dimensions without coordinates: time_input\n", "Data variables:\n", " tasmax (sample, time_input) float32 238.8 235.2 234.7 ... 245.5 242.9" ] }, "execution_count": 9, "metadata": {}, "output_type": "execute_result" } ], "source": [ "n_timepoint_in_each_sample = 10\n", "n_timepoint_in_each_batch = 20\n", "input_overlap = 9\n", "\n", "bgen = xbatcher.BatchGenerator(\n", " ds=ds,\n", " input_dims={\"time\": n_timepoint_in_each_sample},\n", " batch_dims={\"time\": n_timepoint_in_each_batch},\n", " concat_input_dims=True,\n", " input_overlap={\"time\": input_overlap},\n", ")\n", "\n", "n_batch = 0\n", "for batch in bgen:\n", " n_batch += 1\n", "\n", "print(f\"{n_batch} batches\")\n", "batch" ] }, { "cell_type": "markdown", "id": "harmful-benefit", "metadata": {}, "source": [ "We can inspect the samples in a batch for a lat/lon pixel, noting that the overlap only applies within a batch and not across. Thus, within the 20 time points in a batch, we can get 11 samples each with 10 time points and 9 time points allowed to overlap." ] }, { "cell_type": "code", "execution_count": 10, "id": "earlier-warehouse", "metadata": {}, "outputs": [ { "data": { "text/html": [ "
\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "\n", "
<xarray.Dataset>\n",
       "Dimensions:      (input_batch: 11, time_input: 10)\n",
       "Coordinates:\n",
       "    time         (input_batch, time_input) datetime64[ns] 1850-02-10T12:00:00...\n",
       "  * input_batch  (input_batch) int64 0 1 2 3 4 5 6 7 8 9 10\n",
       "Dimensions without coordinates: time_input\n",
       "Data variables:\n",
       "    tasmax       (input_batch, time_input) float32 238.8 235.2 ... 226.3 227.0
" ], "text/plain": [ "\n", "Dimensions: (input_batch: 11, time_input: 10)\n", "Coordinates:\n", " time (input_batch, time_input) datetime64[ns] 1850-02-10T12:00:00...\n", " * input_batch (input_batch) int64 0 1 2 3 4 5 6 7 8 9 10\n", "Dimensions without coordinates: time_input\n", "Data variables:\n", " tasmax (input_batch, time_input) float32 238.8 235.2 ... 226.3 227.0" ] }, "metadata": {}, "output_type": "display_data" }, { "name": "stdout", "output_type": "stream", "text": [ "sample 1 goes from 1850-02-10T12:00:00.000000000 to 1850-02-19T12:00:00.000000000\n", "sample 2 goes from 1850-02-11T12:00:00.000000000 to 1850-02-20T12:00:00.000000000\n" ] } ], "source": [ "lat = -90\n", "lon = 0\n", "pixel = batch.sel(lat=lat, lon=lon)\n", "display(pixel)\n", "\n", "print(\n", " f\"sample 1 goes from {pixel.isel(input_batch=0).time[0].values} to {pixel.isel(input_batch=0).time[-1].values}\"\n", ")\n", "print(\n", " f\"sample 2 goes from {pixel.isel(input_batch=1).time[0].values} to {pixel.isel(input_batch=1).time[-1].values}\"\n", ")" ] }, { "cell_type": "markdown", "id": "arranged-telephone", "metadata": {}, "source": [ "## Example applications\n", "\n", "These batches can then be used to train a downstream machine learning model while preserving the indices of these sample. \n", "\n", "As an example, let's say we want to train a simple CNN model to predict the max air temprature for each day at each lat/lon pixel. To predict the temperature at lat/lon/time of (i, j, t), we'll use features including the temperature of a 9 x 9 grid centered at (i, j), from times t-10 to t-1 (shape of input should be (n_samples_in_each_batch, 9, 9, 9)). Note that in this example, we subset the dataset to a smaller domain for efficiency." ] }, { "cell_type": "code", "execution_count": 11, "id": "consolidated-chocolate", "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "batch 0\n", "feature shape (600, 9, 9, 9)\n", "label shape (600,)\n", "shape of lat of each sample (600,)\n", "\n", "batch 1\n", "feature shape (600, 9, 9, 9)\n", "label shape (600,)\n", "shape of lat of each sample (600,)\n", "\n" ] } ], "source": [ "bgen = xbatcher.BatchGenerator(\n", " ds=ds[[\"tasmax\"]].isel(lat=slice(0, 18), lon=slice(0, 18), time=slice(0, 30)),\n", " input_dims={\"lat\": 9, \"lon\": 9, \"time\": 10},\n", " batch_dims={\"lat\": 18, \"lon\": 18, \"time\": 15},\n", " concat_input_dims=True,\n", " input_overlap={\"lat\": 8, \"lon\": 8, \"time\": 9},\n", ")\n", "\n", "for i, batch in enumerate(bgen):\n", " print(f\"batch {i}\")\n", " # make sure the ordering of dimension is consistent\n", " batch = batch.transpose(\"input_batch\", \"lat_input\", \"lon_input\", \"time_input\")\n", "\n", " # only use the first 9 time points as features, since the last time point is the label to be predicted\n", " features = batch.tasmax.isel(time_input=slice(0, 9))\n", " # select the center pixel at the last time point to be the label to be predicted\n", " # the actual lat/lon/time for each of the sample can be accessed in labels.coords\n", " labels = batch.tasmax.isel(lat_input=5, lon_input=5, time_input=9)\n", "\n", " print(\"feature shape\", features.shape)\n", " print(\"label shape\", labels.shape)\n", " print(\"shape of lat of each sample\", labels.coords[\"lat\"].shape)\n", " print(\"\")" ] }, { "cell_type": "markdown", "id": "legislative-closer", "metadata": {}, "source": [ "We can also use the Xarray's \"stack\" method to transform these into 2D inputs (n_samples, n_features) suitable for other machine learning algorithms implemented in libraries such as [sklearn](https://scikit-learn.org/stable/) and [xgboost](https://xgboost.readthedocs.io/en/stable/). In this case, we are expecting 9 x 9 x 9 = 729 features total." ] }, { "cell_type": "code", "execution_count": 12, "id": "advisory-chicken", "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "batch 0\n", "feature shape (600, 729)\n", "label shape (600,)\n", "shape of lat of each sample (600,) \n", "\n", "batch 1\n", "feature shape (600, 729)\n", "label shape (600,)\n", "shape of lat of each sample (600,) \n", "\n" ] } ], "source": [ "for i, batch in enumerate(bgen):\n", " print(f\"batch {i}\")\n", " # make sure the ordering of dimension is consistent\n", " batch = batch.transpose(\"input_batch\", \"lat_input\", \"lon_input\", \"time_input\")\n", "\n", " # only use the first 9 time points as features, since the last time point is the label to be predicted\n", " features = batch.tasmax.isel(time_input=slice(0, 9))\n", " features = features.stack(features=[\"lat_input\", \"lon_input\", \"time_input\"])\n", "\n", " # select the center pixel at the last time point to be the label to be predicted\n", " # the actual lat/lon/time for each of the sample can be accessed in labels.coords\n", " labels = batch.tasmax.isel(lat_input=5, lon_input=5, time_input=9)\n", "\n", " print(\"feature shape\", features.shape)\n", " print(\"label shape\", labels.shape)\n", " print(\"shape of lat of each sample\", labels.coords[\"lat\"].shape, \"\\n\")" ] }, { "cell_type": "markdown", "id": "persistent-culture", "metadata": {}, "source": [ "## What's next?\n", "\n", "There are many additional useful features that were yet to be implemented in the context of batch generation for downstream machine learning model training purposes. One of the current efforts is to improve the set of data loaders. \n", "\n", "Additional features of interest can include: \n", "\n", "1. Handling overlaps across batches. The common use case of batching in machine learning training involves generating all samples, then group them into batches. When overlap is enabled, this yields different results compared to first generating batches then creating possible samples within each batch. \n", "\n", "2. Shuffling/randomization of samples across batches. It is often desirable for each batch to be grouped randomly instead of along a specific dimension. \n", "\n", "3. Be efficient in terms of memory usage. In the case where overlap is enabled, each sample would comprised of mostly repetitive values compared to adjacent samples. It would be beneficial if each batch/sample is generated lazily to avoid storing these extra duplicative values. \n", "\n", "4. Handling preprocessing steps. For example, data augmentation, scaling/normalization, outlier detection, etc. \n", "\n", "\n", "More thoughts on 1. and 2. can be found in [this issue](https://github.com/xarray-contrib/xbatcher/issues/30). Interested users are welcomed to comment or submit other issues in GitHub. " ] } ], "metadata": { "kernelspec": { "display_name": "Python 3", "language": "python", "name": "python3" }, "language_info": { "codemirror_mode": { "name": "ipython", "version": 3 }, "file_extension": ".py", "mimetype": "text/x-python", "name": "python", "nbconvert_exporter": "python", "pygments_lexer": "ipython3", "version": "3.8.6" } }, "nbformat": 4, "nbformat_minor": 5 }