{ "cells": [ { "cell_type": "code", "execution_count": null, "metadata": { "collapsed": false }, "outputs": [], "source": [ "%matplotlib inline" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "\n# Filling the area between lines\n\n\nThis example shows how to use `~.axes.Axes.fill_between` to color the area\nbetween two lines.\n" ] }, { "cell_type": "code", "execution_count": null, "metadata": { "collapsed": false }, "outputs": [], "source": [ "import matplotlib.pyplot as plt\nimport numpy as np" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Basic usage\n-----------\nThe parameters *y1* and *y2* can be a scalar, indicating a horizontal\nboundary a the given y-values. If only *y1* is given, *y2* defaults to 0.\n\n" ] }, { "cell_type": "code", "execution_count": null, "metadata": { "collapsed": false }, "outputs": [], "source": [ "x = np.arange(0.0, 2, 0.01)\ny1 = np.sin(2 * np.pi * x)\ny2 = 0.8 * np.sin(4 * np.pi * x)\n\nfig, (ax1, ax2, ax3) = plt.subplots(3, 1, sharex=True, figsize=(6, 6))\n\nax1.fill_between(x, y1)\nax1.set_title('fill between y1 and 0')\n\nax2.fill_between(x, y1, 1)\nax2.set_title('fill between y1 and 1')\n\nax3.fill_between(x, y1, y2)\nax3.set_title('fill between y1 and y2')\nax3.set_xlabel('x')\nfig.tight_layout()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Example: Confidence bands\n-------------------------\nA common application for `~.axes.Axes.fill_between` is the indication of\nconfidence bands.\n\n`~.axes.Axes.fill_between` uses the colors of the color cycle as the fill\ncolor. These may be a bit strong when applied to fill areas. It is\ntherefore often a good practice to lighten the color by making the area\nsemi-transparent using *alpha*.\n\n" ] }, { "cell_type": "code", "execution_count": null, "metadata": { "collapsed": false }, "outputs": [], "source": [ "# sphinx_gallery_thumbnail_number = 2\n\nN = 21\nx = np.linspace(0, 10, 11)\ny = [3.9, 4.4, 10.8, 10.3, 11.2, 13.1, 14.1, 9.9, 13.9, 15.1, 12.5]\n\n# fit a linear curve an estimate its y-values and their error.\na, b = np.polyfit(x, y, deg=1)\ny_est = a * x + b\ny_err = x.std() * np.sqrt(1/len(x) +\n (x - x.mean())**2 / np.sum((x - x.mean())**2))\n\nfig, ax = plt.subplots()\nax.plot(x, y_est, '-')\nax.fill_between(x, y_est - y_err, y_est + y_err, alpha=0.2)\nax.plot(x, y, 'o', color='tab:brown')" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Selectively filling horizontal regions\n--------------------------------------\nThe parameter *where* allows to specify the x-ranges to fill. It's a boolean\narray with the same size as *x*.\n\nOnly x-ranges of contiguous *True* sequences are filled. As a result the\nrange between neighboring *True* and *False* values is never filled. This\noften undesired when the data points should represent a contiguous quantity.\nIt is therefore recommended to set ``interpolate=True`` unless the\nx-distance of the data points is fine enough so that the above effect is not\nnoticeable. Interpolation approximates the actual x position at which the\n*where* condition will change and extends the filling up to there.\n\n" ] }, { "cell_type": "code", "execution_count": null, "metadata": { "collapsed": false }, "outputs": [], "source": [ "x = np.array([0, 1, 2, 3])\ny1 = np.array([0.8, 0.8, 0.2, 0.2])\ny2 = np.array([0, 0, 1, 1])\n\nfig, (ax1, ax2) = plt.subplots(2, 1, sharex=True)\n\nax1.set_title('interpolation=False')\nax1.plot(x, y1, 'o--')\nax1.plot(x, y2, 'o--')\nax1.fill_between(x, y1, y2, where=(y1 > y2), color='C0', alpha=0.3)\nax1.fill_between(x, y1, y2, where=(y1 < y2), color='C1', alpha=0.3)\n\nax2.set_title('interpolation=True')\nax2.plot(x, y1, 'o--')\nax2.plot(x, y2, 'o--')\nax2.fill_between(x, y1, y2, where=(y1 > y2), color='C0', alpha=0.3,\n interpolate=True)\nax2.fill_between(x, y1, y2, where=(y1 <= y2), color='C1', alpha=0.3,\n interpolate=True)\nfig.tight_layout()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "

#### Note

Similar gaps will occur if *y1* or *y2* are masked arrays. Since missing\n values cannot be approximated, *interpolate* has no effect in this case.\n The gaps around masked values can only be reduced by adding more data\n points close to the masked values.

\n\n" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Selectively marking horizontal regions across the whole Axes\n------------------------------------------------------------\nThe same selection mechanism can be applied to fill the full vertical height\nof the axes. To be independent of y-limits, we add a transform that\ninterprets the x-values in data coorindates and the y-values in axes\ncoordinates.\n\nThe following example marks the regions in which the y-data are above a\ngiven threshold.\n\n" ] }, { "cell_type": "code", "execution_count": null, "metadata": { "collapsed": false }, "outputs": [], "source": [ "fig, ax = plt.subplots()\nx = np.arange(0, 4 * np.pi, 0.01)\ny = np.sin(x)\nax.plot(x, y, color='black')\n\nthreshold = 0.75\nax.axhline(threshold, color='green', lw=2, alpha=0.7)\nax.fill_between(x, 0, 1, where=y > threshold,\n color='green', alpha=0.5, transform=ax.get_xaxis_transform())" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "------------\n\nReferences\n\"\"\"\"\"\"\"\"\"\"\n\nThe use of the following functions, methods and classes is shown\nin this example:\n\n" ] }, { "cell_type": "code", "execution_count": null, "metadata": { "collapsed": false }, "outputs": [], "source": [ "import matplotlib\nmatplotlib.axes.Axes.fill_between\nmatplotlib.pyplot.fill_between\nmatplotlib.axes.Axes.get_xaxis_transform" ] } ], "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.1" } }, "nbformat": 4, "nbformat_minor": 0 }