data-science-ipython-notebooks/matplotlib/04.07-Customizing-Colorbars.ipynb

570 lines
425 KiB
Python
Raw Normal View History

{
"cells": [
{
"cell_type": "markdown",
"metadata": {},
"source": [
"<!--BOOK_INFORMATION-->\n",
"<img align=\"left\" style=\"padding-right:10px;\" src=\"figures/PDSH-cover-small.png\">\n",
"*This notebook contains an excerpt from the [Python Data Science Handbook](http://shop.oreilly.com/product/0636920034919.do) by Jake VanderPlas; the content is available [on GitHub](https://github.com/jakevdp/PythonDataScienceHandbook).*\n",
"\n",
"*The text is released under the [CC-BY-NC-ND license](https://creativecommons.org/licenses/by-nc-nd/3.0/us/legalcode), and code is released under the [MIT license](https://opensource.org/licenses/MIT). If you find this content useful, please consider supporting the work by [buying the book](http://shop.oreilly.com/product/0636920034919.do)!*\n",
"\n",
"*No changes were made to the contents of this notebook from the original.*"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"<!--NAVIGATION-->\n",
"< [Customizing Plot Legends](04.06-Customizing-Legends.ipynb) | [Contents](Index.ipynb) | [Multiple Subplots](04.08-Multiple-Subplots.ipynb) >"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"# Customizing Colorbars"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Plot legends identify discrete labels of discrete points.\n",
"For continuous labels based on the color of points, lines, or regions, a labeled colorbar can be a great tool.\n",
"In Matplotlib, a colorbar is a separate axes that can provide a key for the meaning of colors in a plot.\n",
"Because the book is printed in black-and-white, this section has an accompanying online supplement where you can view the figures in full color (https://github.com/jakevdp/PythonDataScienceHandbook).\n",
"We'll start by setting up the notebook for plotting and importing the functions we will use:"
]
},
{
"cell_type": "code",
"execution_count": 1,
"metadata": {
"collapsed": true
},
"outputs": [],
"source": [
"import matplotlib.pyplot as plt\n",
"plt.style.use('classic')"
]
},
{
"cell_type": "code",
"execution_count": 2,
"metadata": {
"collapsed": false
},
"outputs": [],
"source": [
"%matplotlib inline\n",
"import numpy as np"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"As we have seen several times throughout this section, the simplest colorbar can be created with the ``plt.colorbar`` function:"
]
},
{
"cell_type": "code",
"execution_count": 3,
"metadata": {
"collapsed": false
},
"outputs": [
{
"data": {
"image/png": "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\nsVEe0aWwiscqIDw/pCW
"text/plain": [
"<matplotlib.figure.Figure at 0x10c21c630>"
]
},
"metadata": {},
"output_type": "display_data"
}
],
"source": [
"x = np.linspace(0, 10, 1000)\n",
"I = np.sin(x) * np.cos(x[:, np.newaxis])\n",
"\n",
"plt.imshow(I)\n",
"plt.colorbar();"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"We'll now discuss a few ideas for customizing these colorbars and using them effectively in various situations."
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Customizing Colorbars\n",
"\n",
"The colormap can be specified using the ``cmap`` argument to the plotting function that is creating the visualization:"
]
},
{
"cell_type": "code",
"execution_count": 4,
"metadata": {
"collapsed": false
},
"outputs": [
{
"data": {
"image/png": "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\nF4l693HUcRIdwGygRPq
"text/plain": [
"<matplotlib.figure.Figure at 0x10d902588>"
]
},
"metadata": {},
"output_type": "display_data"
}
],
"source": [
"plt.imshow(I, cmap='gray');"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"All the available colormaps are in the ``plt.cm`` namespace; using IPython's tab-completion will give you a full list of built-in possibilities:\n",
"```\n",
"plt.cm.<TAB>\n",
"```\n",
"But being *able* to choose a colormap is just the first step: more important is how to *decide* among the possibilities!\n",
"The choice turns out to be much more subtle than you might initially expect."
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"### Choosing the Colormap\n",
"\n",
"A full treatment of color choice within visualization is beyond the scope of this book, but for entertaining reading on this subject and others, see the article [\"Ten Simple Rules for Better Figures\"](http://journals.plos.org/ploscompbiol/article?id=10.1371/journal.pcbi.1003833).\n",
"Matplotlib's online documentation also has an [interesting discussion](http://Matplotlib.org/1.4.1/users/colormaps.html) of colormap choice.\n",
"\n",
"Broadly, you should be aware of three different categories of colormaps:\n",
"\n",
"- *Sequential colormaps*: These are made up of one continuous sequence of colors (e.g., ``binary`` or ``viridis``).\n",
"- *Divergent colormaps*: These usually contain two distinct colors, which show positive and negative deviations from a mean (e.g., ``RdBu`` or ``PuOr``).\n",
"- *Qualitative colormaps*: these mix colors with no particular sequence (e.g., ``rainbow`` or ``jet``).\n",
"\n",
"The ``jet`` colormap, which was the default in Matplotlib prior to version 2.0, is an example of a qualitative colormap.\n",
"Its status as the default was quite unfortunate, because qualitative maps are often a poor choice for representing quantitative data.\n",
"Among the problems is the fact that qualitative maps usually do not display any uniform progression in brightness as the scale increases.\n",
"\n",
"We can see this by converting the ``jet`` colorbar into black and white:"
]
},
{
"cell_type": "code",
"execution_count": 5,
"metadata": {
"collapsed": false
},
"outputs": [],
"source": [
"from matplotlib.colors import LinearSegmentedColormap\n",
"\n",
"def grayscale_cmap(cmap):\n",
" \"\"\"Return a grayscale version of the given colormap\"\"\"\n",
" cmap = plt.cm.get_cmap(cmap)\n",
" colors = cmap(np.arange(cmap.N))\n",
" \n",
" # convert RGBA to perceived grayscale luminance\n",
" # cf. http://alienryderflex.com/hsp.html\n",
" RGB_weight = [0.299, 0.587, 0.114]\n",
" luminance = np.sqrt(np.dot(colors[:, :3] ** 2, RGB_weight))\n",
" colors[:, :3] = luminance[:, np.newaxis]\n",
" \n",
" return LinearSegmentedColormap.from_list(cmap.name + \"_gray\", colors, cmap.N)\n",
" \n",
"\n",
"def view_colormap(cmap):\n",
" \"\"\"Plot a colormap with its grayscale equivalent\"\"\"\n",
" cmap = plt.cm.get_cmap(cmap)\n",
" colors = cmap(np.arange(cmap.N))\n",
" \n",
" cmap = grayscale_cmap(cmap)\n",
" grayscale = cmap(np.arange(cmap.N))\n",
" \n",
" fig, ax = plt.subplots(2, figsize=(6, 2),\n",
" subplot_kw=dict(xticks=[], yticks=[]))\n",
" ax[0].imshow([colors], extent=[0, 10, 0, 1])\n",
" ax[1].imshow([grayscale], extent=[0, 10, 0, 1])"
]
},
{
"cell_type": "code",
"execution_count": 6,
"metadata": {
"collapsed": false
},
"outputs": [
{
"data": {
"image/png": "iVBORw0KGgoAAAANSUhEUgAAAV0AAABsCAYAAADJ2WELAAAABHNCSVQICAgIfAhkiAAAAAlwSFlz\nAAALEgAACxIB0t1+/AAABCBJREFUeJzt2lFyozgUBdAnyG6yx/noZWVtEZoP29MOAWzS5KUZnVNF\nARIQQK5bKfRKay0AyDH89A0A9EToAiQSugCJhC5AIqELkOhlq7OUorQB4Ataa2WpfTN0L35FxHhd\nXmbr2/aj9qVzH/VtHRcRMXue4e6wteXliWP2Lqe4Zot4qRHjFDHWKOMUwzjFMNYYxxrjdX8c66V9\nmGIoNcaoMcYUQ0wxRo0hphiubR/3fx/3+dilvvk1fvfd2tb/3jN98/te/3vLfWvPvta39p5uz7LQ\nV2uM0xRDnWKoLcYaMdaIoUaUGhE1Iqbrem3/mePen7zOM23TxjX/9J6/eC/tul9rxPt0Wdca8X5d\narvc7u2279dLbfO+tf2ta9SI+CfW+bwAkEjoAiQSugCJhC5AoqTQXZzEI5Ux6FLHw/4dj37ENZNC\nV+XZzzMGXep42L/j0Y+4ps8LAImELkAioQuQyERaN4xBlzoe9s4n0gCIUL3QEWPQpY6HXfUCAEIX\nIJPQBUikeqEbxqBLHQ+76gUAVC/0wxh0qeNhV70AgNAFyCR0ARKpXuiGMehSx8OuegEA1Qv9MAZd\n6njYVS8AIHQBMgldgESqF7phDLrU8bB3Xr3Q8df8v4Yx6FLHw24iDQChC5BJ6AIkKq2tf6UopXT8\nRQjg61pri/Num6ELwLF8XgBIJHQBEgldgERCFyCR0AVIJHQBEgldgERCFyCR0AVIJHQBEgldgERC\nFyCR0AVIJHQBEgldgERCFyCR0AVIJHQBEgldgERCFyCR0AVIJHQBEgldgERCFyCR0AVI9LLVWUpp\nWTcC8H/SWitL7ZuhGxHx+voapZQYhss/xcMwRCnlw7LUttS+dY21/nnbbf8ZpZRP27fr3m8/Wpae\n47a+317qe9Q+juOn9qVlfuw4jh+ueb9/257vz6+x9vfn7+76A3r4vp85Zm18nu2bt6/tr4390nnz\n/mfW97+jpbZH/RGX93V7Z9M0/bd/275f35a1/q3z9pyzdg9rffN7X9q/P+9+f95///tZa1vajoio\ntX54T2tLay1qravv9dF5W9e4X97e3mKNzwsAiYQuQCKhC5BI6AIkErqww9bk39/oO+73bO/gSEc8\nu9CFHfZWaPy077jfs72DIx3x7EIXIJHQBUgkdAESCV3Y4WyTSCbSjmUiDeBkhC7scLaZe9ULx1K9\nAHAyQhcgkdAFSCR0YYezzdyrXjiW6gWAkxG6sMPZZu5VLxxL9QLAyQhdgERCFyCR0IUdzjZzr3rh\nWKoXAE5G6MIOZ5u5V71wLNULACcjdAESCV2AREIXdjjbzL3qhWOpXoBkZ5tEMpF2LBNpACcjdAES\nCV2ARGXrG0Uppd+PNwB/oLW2OOu2GboAHMvnBYBEQhcgkdAFSCR0ARIJXYBE/wLuUZ/r1NIE0gAA\nAABJRU5ErkJggg==\n",
"text/plain": [
"<matplotlib.figure.Figure at 0x11656ceb8>"
]
},
"metadata": {},
"output_type": "display_data"
}
],
"source": [
"view_colormap('jet')"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Notice the bright stripes in the grayscale image.\n",
"Even in full color, this uneven brightness means that the eye will be drawn to certain portions of the color range, which will potentially emphasize unimportant parts of the dataset.\n",
"It's better to use a colormap such as ``viridis`` (the default as of Matplotlib 2.0), which is specifically constructed to have an even brightness variation across the range.\n",
"Thus it not only plays well with our color perception, but also will translate well to grayscale printing:"
]
},
{
"cell_type": "code",
"execution_count": 7,
"metadata": {
"collapsed": false
},
"outputs": [
{
"data": {
"image/png": "iVBORw0KGgoAAAANSUhEUgAAAV0AAABsCAYAAADJ2WELAAAABHNCSVQICAgIfAhkiAAAAAlwSFlz\nAAALEgAACxIB0t1+/AAABBlJREFUeJzt2lGSokgQBuBMevYS+9Qn6FPMEeb8exRrH1QERxBUcmT6\n+yIMyaIqwY6O/wEqW2sBQI3uT98AwHcidAEKCV2AQkIXoJDQBSj0Y+5kZtraAPCA1lreGp8N3YiI\nn/krIjMiu4iMyOyOdXfsl92pzozoutNYjtb05wd19mPXnxjV7cZYRByvP6hbfw+nG+/XntfHVb8Y\nn+97RD/W+jXDnnG1frAuYrQuIqJ1g7HrHhH9cTv/rhyOTfScPH+7Hs2/cZ3hnJtrYvibJ64502Nc\nt9meo3p0nXbnt7ZRj8s1229jEW1c5+06Rz1b/6frz2VExnFOXq3J0/FsHS26vKzvBnMyLsfd+V8+\nzvVxTZeX+nj747rrj1t0eejHRnP6NYfozufjsu7jPD8u48e5w+tc6vH36ZpxGKwb1HG+xqG/j484\nDNYer99FG605n798n3pe16c5H8N77+sY9+vruHwyruo8HefguIuMjI/MyMjjucj459//YorHCwCF\nhC5AIaELUEjoAhQSurBG3p/y9/d8YfMt7nMLL7xPoQtrbLGJcnc9X9h8L5tSX3ifQhegkNAFKCR0\nAQoJXVhjdy+9tujpRdozhC5AIaELa+xup8EWPe1eeIbQBSgkdAEKCV2AQkIX1tjdToMtetq98Ayh\nC1BI6MIau9tpsEVPuxeeIXQBCgldgEJCF6CQ0IU1drfTYIuedi88Q+gCFBK6sMbudhps0dPuhWcI\nXYBCQhegkNAFKCR0YY3d7TTYoqfdC88QurDG7l56bdHTi7RnCF2AQkIXoJDQBSiUrU0/rMjMvTxx\nAXgrrbWbr99mQxeA1/J4AaCQ0AUoJHQBCgldgEJCF6CQ0AUoJHQBCgldgEJCF6CQ0AUoJHQBCgld\ngEJCF6CQ0AUoJHQBCgldgEJCF6CQ0AUoJHQBCgldgEJCF6CQ0AUoJHQBCgldgEJCF6DQj7mTmdmq\nbgTgb9Jay1vjs6EbEfH19RWZl7Xn46nv8/Haeup7ybq1PZeuWXLNR3s+Mv/eb3lk/pqeU+uf/W1b\n/H/dOveKHlM9X/n9yNxhPTe2tsfc+bU97t3DvTV/oudUfT3Wdd2o/vz8jCkeLwAUEroAhYQuQCGh\nC1BI6AKLDF+W6fk4oQss0trrd5B+x55CF6CQ0AUoJHQBCgldYJF3f0G1l55CF6CQ0AUWefddAXvp\nKXQBCgldgEJCF6CQ0AUWefddAXvpKXQBCgldYJF33xWwl55CF6CQ0AUoJHQBCgldYJF33xWwl55C\nF6CQ0AUWefddAXvpKXQBCgldgEJCF6CQ0AUWefddAXvpKXSBRd79BdVeegpdgEJCF6CQ0AUolHPP\nKjLz9Q9HAL6B1trNt2+zoQvAa3m8AFBI6AIUEroAhYQuQCGhC1Dof8izEtxDEuLdAAAAAElFTkSu\nQmCC\n",
"text/plain": [
"<matplotlib.figure.Figure at 0x1165767f0>"
]
},
"metadata": {},
"output_type": "display_data"
}
],
"source": [
"view_colormap('viridis')"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"If you favor rainbow schemes, another good option for continuous data is the ``cubehelix`` colormap:"
]
},
{
"cell_type": "code",
"execution_count": 8,
"metadata": {
"collapsed": false
},
"outputs": [
{
"data": {
"image/png": "iVBORw0KGgoAAAANSUhEUgAAAV0AAABsCAYAAADJ2WELAAAABHNCSVQICAgIfAhkiAAAAAlwSFlz\nAAALEgAACxIB0t1+/AAABDNJREFUeJzt3OtyokAQBtDuMe//yrM/GECNcSUFLe6ek7KkGex4gW9T\nztRm7z0AqNHe/QQA/idCF6CQ0AUoJHQBCgldgEJfzwYz09IGgF/oveej/U9Dd5aR0XL6o7hFi8yM\nNv5IzmzRskVGRmabjh51u65zHY8Hx0eu95HtZnv+PZEZ0dYeU51T3XI9PiMiW/RlPKbHZa77Mr7X\n7WrfTR03dYynMO/ry1hEZF+e3nUdrS+PyeyP64jI1iNz3Ma+yD5e+jgm+8NbG/9GttGzZZ9+9byd\nPVqs+6aX0qMtx8TV+BgbL/cSa51LPcZy3s6rY6f6crV/ri/LcTnG2lr3No67Hvtet/mn39VXPxkZ\nLS53+8Z9tmij67ffkHM99uV8v76Kdd94haOOpR5jub4jS53juHk7cql7toh2Wc7xm7pNdb+6Fvpy\nzucYy/VcX8an7ciIPq6Tnnf1+GDX8fUauL5G+nwNLNsRN9dPXF0LP9bTubee/4/3Za77clxL8+Wc\nud6my7+v9XIN3F2uc5251rHWbTk+R4+8G5/OkBz36zG53o/xS7vET3y9AFBI6AIUEroAhYQuQCGh\nCxs8nI7m1454P/PkTYUubGAN5b6OeD8P+T+8dmwqdAEKCV2AQkIXoJDQhQ1MpO3r5HNehzQVugCF\nhC5sYPXCvk6+0OCQpkIXoJDQBSgkdAEKCV3YwOqFfZ18ocEhTYUuQCGhCxtYvbCvky80OKSp0AUo\nJHQBCgldgEJCFzawemFfJ19ocEhToQtQSOjCBlYv7OvkCw0OaSp0AQoJXYBCQhegkNCFDaxe2NfJ\nFxoc0lTowgYm0vZ18jmvQ5oKXYBCQhegkNAFKJT9yXcVmekrLIBf6L0/nH17GroA7MvXCwCFhC5A\nIaELUEjoAhQSugCFhC5AIaELUEjoAhQSugCFhC5AIaELUEjoAhQSugCFhC5AIaELUEjoAhQSugCF\nhC5AIaELUEjoAhQSugCFhC5AIaELUEjoAhQSugCFvp4NZmaveiIA/5Leez7a/zR0Z5kZmXmz/ah+\ndPvbY17puUePV3q21l7q2Vr78Xm+2uOV57T1td5/Xs96/u1z3TL+6vPcei5tfT/3Oh+3foZHvfbf\nvt+Pjj/yXNqz/tSe9+/X5XKJn/h6AaCQ0AUoJHQBCgldgEJCF97seiJGz3+/p9CFN+t9/5WZep63\np9AFKCR0AQoJXYBCQhfe7OwTP3qaSAP4WEIX3uzss+16Wr0A8LGELkAhoQtQSOjCm519tl1PqxcA\nPpbQhTc7+2y7nlYvAHwsoQtQSOgCFBK68GZnn23X0+oFgI8ldOHNzj7brqfVCwAfS+gCFBK6AIWE\nLrzZ2Wfb9bR6Af4pZ5/40dNEGsDHEroAhYQuQKGvVw7qvR/yPQnA/yaFKUAdXy8AFBK6AIWELkAh\noQtQSOgCFPoDAVPczXaO6jAAAAAASUVORK5CYII=\n",
"text/plain": [
"<matplotlib.figure.Figure at 0x1165caf60>"
]
},
"metadata": {},
"output_type": "display_data"
}
],
"source": [
"view_colormap('cubehelix')"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"For other situations, such as showing positive and negative deviations from some mean, dual-color colorbars such as ``RdBu`` (*Red-Blue*) can be useful. However, as you can see in the following figure, it's important to note that the positive-negative information will be lost upon translation to grayscale!"
]
},
{
"cell_type": "code",
"execution_count": 9,
"metadata": {
"collapsed": false
},
"outputs": [
{
"data": {
"image/png": "iVBORw0KGgoAAAANSUhEUgAAAV0AAABsCAYAAADJ2WELAAAABHNCSVQICAgIfAhkiAAAAAlwSFlz\nAAALEgAACxIB0t1+/AAABXVJREFUeJzt3GuO2zYUBtBLOfvoOrKjrqpLShdUWOwPPaz4NZmMfENa\n5wCGTIm6pungw0AkUmqtAUCO4U8PAOBIhC5AIqELkEjoAiQSugCJvj27WEqxtQHgN9Ray73zT0M3\nIuLv+CuGiBjK9GfxqZTpfSlze35f5mtL31Kma7F5f3V9iLipcf0ZpxJRSsQwDFGGEuVUIpb2qUzn\nhogyt4dhul5OU/9hLjrM7VLK5r7pNUwDuLSnD49huO47rMdY2/PnnIaIsulz2vYpMQxDxKb/UmM4\nDdOYlpqnuU8p63fYtpcaUab3Ue61T5t+JWJpb/rcbc/95gmPUrbt06X/cq5sjlGiXrWjDFHL/ANO\nP1pEmfvF7f0/9V/ODcu5n++ZakSMNaJGRF2PNep8frpe1+v3zl2OdXP9Ume9XiPGqJvrl88b61yz\n1jgvfWudXxFjRIxjXc/ViLlfnc7PNdd7xpi/Q/25zqZPjYhx3PSJiPPyGePU/zzW9dx5Pjeu7XFt\nnzf3LO3zpsZ1zfFRzVqneRmnuZiO81xu28v1tf/l3DhP7Nqef5Sf2ss9j/rXGnU8Rx3HqHWMOp4j\n6hjjVbuOl9farudN+xx1vi/qGPV8W/NR+79//3mYqR4vACQSugCJhC5AIqELkOgQoXt3CfEgNV/h\nJeNM+PKl14F/wUu+85Fr7uAQofuKfW+91HyFl4wz4cu/5v92avtXe8l3PnLNHRwidAFaIXQBEgld\ngESHCN1entE3+tz/Rq/rURbS9ip64Jo7OEToArTiEKHby8Joo4utN3rdBGD3wl5FD1xzB4cIXYBW\nCF2AREIXINEhQreXhdFGF1tv9LoJwO6FvYoeuOYODhG6AK04ROj2sjDa6GLrjV43Adi9sFfRA9fc\nwSFCF6AVQhcgkdAFSHSI0O1lYbTRxdYbvW4CsHthr6IHrrmDQ4QuQCsOEbq9LIw2uth6o9dNAHYv\n7FX0wDV3cIjQBWiF0AVIJHQBEh0idHtZGG10sfVGr5sA7F7Yq+iBa+7gEKHbyzP6Rp/73+h1PcpC\n2l5FD1xzB4cIXYBWCF2AREIXIFGpTx76lFIafSoC0LZa692lvKehC8C+PF4ASCR0ARIJXYBEQhcg\nkdAFSCR0ARIJXYBEQhcgkdAFSCR0ARIJXYBEQhcgkdAFSCR0ARIJXYBEQhcgkdAFSCR0ARIJXYBE\nQhcgkdAFSCR0ARIJXYBEQhcgkdAFSPTt2cVSSs0aCMA7qbWWe+efhm5ExPfv36OUEsMwRCllfW3b\ny/thmP5w/kr7Uc3t+Xvt6/Hdu/7oOzwbx3W/RzU/c+9Hx1+t8dHr3tx89Bt8VON6/ku5/Lt6dm55\nf3381fsf1ai1rq+lfX2812d5/6jGZ2puX+M4RkTEOI6fvv7RPR/VWNrb4/X7e30+c/yoz+9+98/0\n+dW5+ep3/Wg+7/1mS/vHjx/xiMcLAImELkAioQuQSOgCJBK6b267KHW0mn/iM76il3ltfR4XrY5T\n6L657Sr90Wr+ic/4il7mtfV5XLQ6TqELkEjoAiQSugCJhO6b62UhxUJaP/Pa+jwuWh2n0AVIJHTf\nXC+r13Yv9DOvrc/jotVxCl2AREIXIJHQBUgkdN9cL6vXdi/0M6+tz+Oi1XEKXYBEQvfN9bJ6bfdC\nP/Pa+jwuWh2n0AVIJHQBEgldgERC9831snpt90I/89r6PC5aHafQBUgkdN9cL6vXdi/0M6+tz+Oi\n1XEKXYBEQhcgkdAFSCR031wvq9d2L/Qzr63P46LVcQrdN9fLQoqFtH7mtfV5XLQ6TqELkEjoAiQS\nugCJyrPnHqWUNh+KADSu1np3Je9p6AKwL48XABIJXYBEQhcgkdAFSCR0ARL9D81xLwk8NAnaAAAA\nAElFTkSuQmCC\n",
"text/plain": [
"<matplotlib.figure.Figure at 0x10c20e908>"
]
},
"metadata": {},
"output_type": "display_data"
}
],
"source": [
"view_colormap('RdBu')"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"We'll see examples of using some of these color maps as we continue.\n",
"\n",
"There are a large number of colormaps available in Matplotlib; to see a list of them, you can use IPython to explore the ``plt.cm`` submodule. For a more principled approach to colors in Python, you can refer to the tools and documentation within the Seaborn library (see [Visualization With Seaborn](04.14-Visualization-With-Seaborn.ipynb))."
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"### Color limits and extensions\n",
"\n",
"Matplotlib allows for a large range of colorbar customization.\n",
"The colorbar itself is simply an instance of ``plt.Axes``, so all of the axes and tick formatting tricks we've learned are applicable.\n",
"The colorbar has some interesting flexibility: for example, we can narrow the color limits and indicate the out-of-bounds values with a triangular arrow at the top and bottom by setting the ``extend`` property.\n",
"This might come in handy, for example, if displaying an image that is subject to noise:"
]
},
{
"cell_type": "code",
"execution_count": 10,
"metadata": {
"collapsed": false
},
"outputs": [
{
"data": {
"image/png": "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\nDisM2Jo6C+tjU4SQ6BY
"text/plain": [
"<matplotlib.figure.Figure at 0x10d93be48>"
]
},
"metadata": {},
"output_type": "display_data"
}
],
"source": [
"# make noise in 1% of the image pixels\n",
"speckles = (np.random.random(I.shape) < 0.01)\n",
"I[speckles] = np.random.normal(0, 3, np.count_nonzero(speckles))\n",
"\n",
"plt.figure(figsize=(10, 3.5))\n",
"\n",
"plt.subplot(1, 2, 1)\n",
"plt.imshow(I, cmap='RdBu')\n",
"plt.colorbar()\n",
"\n",
"plt.subplot(1, 2, 2)\n",
"plt.imshow(I, cmap='RdBu')\n",
"plt.colorbar(extend='both')\n",
"plt.clim(-1, 1);"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Notice that in the left panel, the default color limits respond to the noisy pixels, and the range of the noise completely washes-out the pattern we are interested in.\n",
"In the right panel, we manually set the color limits, and add extensions to indicate values which are above or below those limits.\n",
"The result is a much more useful visualization of our data."
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"### Discrete Color Bars\n",
"\n",
"Colormaps are by default continuous, but sometimes you'd like to represent discrete values.\n",
"The easiest way to do this is to use the ``plt.cm.get_cmap()`` function, and pass the name of a suitable colormap along with the number of desired bins:"
]
},
{
"cell_type": "code",
"execution_count": 11,
"metadata": {
"collapsed": false
},
"outputs": [
{
"data": {
"image/png": "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\nrhe/aHWQJTCzCr6Si8G
"text/plain": [
"<matplotlib.figure.Figure at 0x116d71940>"
]
},
"metadata": {},
"output_type": "display_data"
}
],
"source": [
"plt.imshow(I, cmap=plt.cm.get_cmap('Blues', 6))\n",
"plt.colorbar()\n",
"plt.clim(-1, 1);"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"The discrete version of a colormap can be used just like any other colormap."
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Example: Handwritten Digits\n",
"\n",
"For an example of where this might be useful, let's look at an interesting visualization of some hand written digits data.\n",
"This data is included in Scikit-Learn, and consists of nearly 2,000 $8 \\times 8$ thumbnails showing various hand-written digits.\n",
"\n",
"For now, let's start by downloading the digits data and visualizing several of the example images with ``plt.imshow()``:"
]
},
{
"cell_type": "code",
"execution_count": 12,
"metadata": {
"collapsed": false
},
"outputs": [
{
"data": {
"image/png": "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\nwdnZmUUh+VSrVQ+f0u/
"text/plain": [
"<matplotlib.figure.Figure at 0x10bb38d30>"
]
},
"metadata": {},
"output_type": "display_data"
}
],
"source": [
"# load images of the digits 0 through 5 and visualize several of them\n",
"from sklearn.datasets import load_digits\n",
"digits = load_digits(n_class=6)\n",
"\n",
"fig, ax = plt.subplots(8, 8, figsize=(6, 6))\n",
"for i, axi in enumerate(ax.flat):\n",
" axi.imshow(digits.images[i], cmap='binary')\n",
" axi.set(xticks=[], yticks=[])"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Because each digit is defined by the hue of its 64 pixels, we can consider each digit to be a point lying in 64-dimensional space: each dimension represents the brightness of one pixel.\n",
"But visualizing relationships in such high-dimensional spaces can be extremely difficult.\n",
"One way to approach this is to use a *dimensionality reduction* technique such as manifold learning to reduce the dimensionality of the data while maintaining the relationships of interest.\n",
"Dimensionality reduction is an example of unsupervised machine learning, and we will discuss it in more detail in [What Is Machine Learning?](05.01-What-Is-Machine-Learning.ipynb).\n",
"\n",
"Deferring the discussion of these details, let's take a look at a two-dimensional manifold learning projection of this digits data (see [In-Depth: Manifold Learning](05.10-Manifold-Learning.ipynb) for details):"
]
},
{
"cell_type": "code",
"execution_count": 13,
"metadata": {
"collapsed": false
},
"outputs": [],
"source": [
"# project the digits into 2 dimensions using IsoMap\n",
"from sklearn.manifold import Isomap\n",
"iso = Isomap(n_components=2)\n",
"projection = iso.fit_transform(digits.data)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"We'll use our discrete colormap to view the results, setting the ``ticks`` and ``clim`` to improve the aesthetics of the resulting colorbar:"
]
},
{
"cell_type": "code",
"execution_count": 14,
"metadata": {
"collapsed": false
},
"outputs": [
{
"data": {
"image/png": "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\nvjue/rXVE0Zv6LaXRxQ
"text/plain": [
"<matplotlib.figure.Figure at 0x1139266d8>"
]
},
"metadata": {},
"output_type": "display_data"
}
],
"source": [
"# plot the results\n",
"plt.scatter(projection[:, 0], projection[:, 1], lw=0.1,\n",
" c=digits.target, cmap=plt.cm.get_cmap('cubehelix', 6))\n",
"plt.colorbar(ticks=range(6), label='digit value')\n",
"plt.clim(-0.5, 5.5)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"The projection also gives us some interesting insights on the relationships within the dataset: for example, the ranges of 5 and 3 nearly overlap in this projection, indicating that some hand written fives and threes are difficult to distinguish, and therefore more likely to be confused by an automated classification algorithm.\n",
"Other values, like 0 and 1, are more distantly separated, and therefore much less likely to be confused.\n",
"This observation agrees with our intuition, because 5 and 3 look much more similar than do 0 and 1.\n",
"\n",
"We'll return to manifold learning and to digit classification in [Chapter 5](05.00-Machine-Learning.ipynb)."
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"<!--NAVIGATION-->\n",
"< [Customizing Plot Legends](04.06-Customizing-Legends.ipynb) | [Contents](Index.ipynb) | [Multiple Subplots](04.08-Multiple-Subplots.ipynb) >"
]
}
],
"metadata": {
"anaconda-cloud": {},
"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.4.3"
}
},
"nbformat": 4,
"nbformat_minor": 0
}