├── .DS_Store
├── .gitignore
├── LICENSE
├── README.md
├── examples
└── faceting.py
├── mlb-data
├── drange
└── scrape-mlb.sh
└── notebooks
├── 00 - The Baseball Data - Cleaning it.ipynb
├── 01 - The Basics - The API, Datasets, Your First ggplot.ipynb
├── 02 - A Case Study - Exploring a baseball dataset.ipynb
├── 03 - Looking for Trends - Colors & Stat Smooth.ipynb
├── 04 - The Strike Zone - scales, labels, and themes.ipynb
├── 05 - What's next.ipynb
├── 06 - Under the Hood.ipynb
├── baseball-pitches-clean.csv
├── baseball-pitches.csv
└── old-tutorials
├── 01 - Baseball.ipynb
├── 01 - Basics - Datasets, Layers, and Geoms.ipynb
└── 02 - Stats, Facets, and Scaling.ipynb
/.DS_Store:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/glamp/ggplot-tutorial/2cc1d4b9b7b35f643a888a57c68c7349a3db6430/.DS_Store
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | # Byte-compiled / optimized / DLL files
2 | __pycache__/
3 | *.py[cod]
4 |
5 | # C extensions
6 | *.so
7 |
8 | # Distribution / packaging
9 | .Python
10 | env/
11 | bin/
12 | build/
13 | develop-eggs/
14 | dist/
15 | eggs/
16 | lib/
17 | lib64/
18 | parts/
19 | sdist/
20 | var/
21 | *.egg-info/
22 | .installed.cfg
23 | *.egg
24 |
25 | # Installer logs
26 | pip-log.txt
27 | pip-delete-this-directory.txt
28 |
29 | # Unit test / coverage reports
30 | htmlcov/
31 | .tox/
32 | .coverage
33 | .cache
34 | nosetests.xml
35 | coverage.xml
36 |
37 | # Translations
38 | *.mo
39 |
40 | # Mr Developer
41 | .mr.developer.cfg
42 | .project
43 | .pydevproject
44 |
45 | # Rope
46 | .ropeproject
47 |
48 | # Django stuff:
49 | *.log
50 | *.pot
51 |
52 | # Sphinx documentation
53 | docs/_build/
54 |
55 | notebooks/.ipynb_checkpoints/
56 |
--------------------------------------------------------------------------------
/LICENSE:
--------------------------------------------------------------------------------
1 | Copyright (c) 2014, Greg Lamp
2 | All rights reserved.
3 |
4 | Redistribution and use in source and binary forms, with or without
5 | modification, are permitted provided that the following conditions are met:
6 |
7 | * Redistributions of source code must retain the above copyright notice, this
8 | list of conditions and the following disclaimer.
9 |
10 | * Redistributions in binary form must reproduce the above copyright notice,
11 | this list of conditions and the following disclaimer in the documentation
12 | and/or other materials provided with the distribution.
13 |
14 | * Neither the name of the {organization} nor the names of its
15 | contributors may be used to endorse or promote products derived from
16 | this software without specific prior written permission.
17 |
18 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
19 | AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
20 | IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
21 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
22 | FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
23 | DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
24 | SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
25 | CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
26 | OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
27 | OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # ggplot for python
2 | ## CFP
3 | Making basic, good-looking plots in Python is tough. Matplotlib gives you great
4 | control, but at the expense of being very detailed. The rise of pandas has made
5 | Python the go-to language for data wrangling and munging but many people are
6 | still reluctant to leave R because of its outstanding data viz packages. ggplot
7 | is a port of the popular R package ggplot2. It provides a high level grammar
8 | that allow users to quickly and easily make good looking plots. So say good-bye
9 | to matplotlib, and hello to ggplot as your everyday Python plotting library!
10 |
11 | ## The Talk
12 |
13 | ### Data
14 | - [https://github.com/slnovak/mlb_terminal](https://github.com/slnovak/mlb_terminal)
15 | - [baseball-pitches-clean.csv](https://s3.amazonaws.com/yhat-examples/baseball-pitches-clean.csv)
16 |
17 | ### Outline
18 | #### Slides (20 mins)
19 | http://www.slideshare.net/Yhat/ggplot-for-python
20 | #### IPython Notebook (40-50 mins) *Safety not guaranteed*
21 | Runing the notebooks
22 | ```bash
23 | $ ipython notebook notebooks/ --pylab inline
24 | ```
25 |
26 | ### Final Thoughts
27 | #### Where it's going
28 | #### Want to help?
29 |
--------------------------------------------------------------------------------
/examples/faceting.py:
--------------------------------------------------------------------------------
1 | import matplotlib.pyplot as plt
2 | import pandas as pd
3 | import numpy as np
4 |
5 | N = 100
6 | industry = ['a','b','c']
7 | city = ['x','y','z']
8 | ind = np.random.choice(industry, N)
9 | cty = np.random.choice(city, N)
10 | jobs = np.random.randint(low=1,high=250,size=N)
11 | df_city =pd.DataFrame({'industry':ind,'city':cty,'jobs':jobs})
12 |
13 | ## how many panels do we need?
14 | cols =df_city.city.value_counts().shape[0]
15 | fig, axes = plt.subplots(1, cols, figsize=(8, 8))
16 |
17 | for x, city in enumerate(df_city.city.value_counts().index.values):
18 | data = df_city[(df_city['city'] == city)]
19 | data = data.groupby(['industry']).jobs.sum()
20 | print (data)
21 | print type(data.index)
22 | left= [k[0] for k in enumerate(data)]
23 | right= [k[1] for k in enumerate(data)]
24 |
25 | axes[x].bar(left,right,label="%s" % (city))
26 | axes[x].set_xticks(left, minor=False)
27 | axes[x].set_xticklabels(data.index.values)
28 |
29 | axes[x].legend(loc='best')
30 | axes[x].grid(True)
31 | fig.suptitle('Employment By Industry By City', fontsize=20)
32 | plt.show(1)
33 |
34 | from ggplot import *
35 |
36 | print ggplot(aes(x='city'), data=df_city) + geom_bar() + facet_grid(x=None, y="city", nrow=1)
37 |
--------------------------------------------------------------------------------
/mlb-data/drange:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env python
2 | import sys
3 | import datetime
4 |
5 | base = datetime.datetime.strptime(sys.argv[1], "%Y-%m-%d")
6 | numdays = int(sys.argv[2])
7 |
8 | for x in range(0, numdays):
9 | print (base - datetime.timedelta(days=x)).strftime("%Y-%m-%d")
10 |
--------------------------------------------------------------------------------
/mlb-data/scrape-mlb.sh:
--------------------------------------------------------------------------------
1 | #!/bin/bash
2 |
3 |
4 |
5 | cat cols-pitch.tsv > pitches.tsv
6 | for current_date in $(./drange 2013-10-01 180)
7 | do
8 | echo "Scraping day ${current_date}"
9 | for i in $(mlb games --date "${current_date}" | cut -f 1)
10 | do
11 | echo " Scraping game #${i}..."
12 | mlb game --date "$current_date" --pitches "${i}" >> pitches.tsv
13 | # mlb game --date yesterday --hits "${i}" >> hits.tsv
14 | done
15 | done
16 |
--------------------------------------------------------------------------------
/notebooks/00 - The Baseball Data - Cleaning it.ipynb:
--------------------------------------------------------------------------------
1 | {
2 | "metadata": {
3 | "name": ""
4 | },
5 | "nbformat": 3,
6 | "nbformat_minor": 0,
7 | "worksheets": [
8 | {
9 | "cells": [
10 | {
11 | "cell_type": "code",
12 | "collapsed": false,
13 | "input": [
14 | "import pandas as pd\n",
15 | "import numpy as np"
16 | ],
17 | "language": "python",
18 | "metadata": {},
19 | "outputs": [],
20 | "prompt_number": 1
21 | },
22 | {
23 | "cell_type": "markdown",
24 | "metadata": {},
25 | "source": [
26 | "## The Data\n",
27 | "The data comes from the MLB [PitchFX](http://www.fangraphs.com/library/misc/pitch-fx/) dataset. It's publicly available and is updated __very__ frequently.\n",
28 | "\n",
29 | "I used [`mlb_terminal`](https://github.com/slnovak/mlb_terminal) to collect 2 months worth of data from the 2013 season. You can see it in the bash script `scrape-mlb.sh`."
30 | ]
31 | },
32 | {
33 | "cell_type": "code",
34 | "collapsed": false,
35 | "input": [
36 | "! open http://gd2.mlb.com/components/game/mlb/year_2012/month_06/day_01/gid_2012_06_01_arimlb_sdnmlb_1/inning/inning_2.xml"
37 | ],
38 | "language": "python",
39 | "metadata": {},
40 | "outputs": [],
41 | "prompt_number": 4
42 | },
43 | {
44 | "cell_type": "code",
45 | "collapsed": false,
46 | "input": [
47 | "df = pd.read_csv(\"./baseball-pitches.csv\")\n",
48 | "df.head()"
49 | ],
50 | "language": "python",
51 | "metadata": {},
52 | "outputs": [
53 | {
54 | "html": [
55 | "
\n",
56 | "<class 'pandas.core.frame.DataFrame'>\n",
57 | "Int64Index: 5 entries, 0 to 4\n",
58 | "Data columns (total 36 columns):\n",
59 | "pitch_time 5 non-null values\n",
60 | "inning 5 non-null values\n",
61 | "top_or_bottom 5 non-null values\n",
62 | "pitcher_name 5 non-null values\n",
63 | "hitter_name 5 non-null values\n",
64 | "pitch_type 5 non-null values\n",
65 | "x 5 non-null values\n",
66 | "y 5 non-null values\n",
67 | "start_speed 5 non-null values\n",
68 | "end_speed 5 non-null values\n",
69 | "sz_top 5 non-null values\n",
70 | "sz_bottom 5 non-null values\n",
71 | "pfx_x 5 non-null values\n",
72 | "pfx_z 5 non-null values\n",
73 | "px 5 non-null values\n",
74 | "pz 5 non-null values\n",
75 | "x0 5 non-null values\n",
76 | "y0 5 non-null values\n",
77 | "ax 5 non-null values\n",
78 | "ay 5 non-null values\n",
79 | "az 5 non-null values\n",
80 | "z0 5 non-null values\n",
81 | "vx0 5 non-null values\n",
82 | "vy0 5 non-null values\n",
83 | "vz0 5 non-null values\n",
84 | "break_y 5 non-null values\n",
85 | "break_angle 5 non-null values\n",
86 | "break_length 5 non-null values\n",
87 | "pitch_name 5 non-null values\n",
88 | "type_confidence 5 non-null values\n",
89 | "zone 5 non-null values\n",
90 | "nasty 5 non-null values\n",
91 | "spin_dir 5 non-null values\n",
92 | "spin_rate 5 non-null values\n",
93 | "comments 0 non-null values\n",
94 | "unk 0 non-null values\n",
95 | "dtypes: float64(28), int64(1), object(7)\n",
96 | "
"
97 | ],
98 | "metadata": {},
99 | "output_type": "pyout",
100 | "prompt_number": 30,
101 | "text": [
102 | "\n",
103 | "Int64Index: 5 entries, 0 to 4\n",
104 | "Data columns (total 36 columns):\n",
105 | "pitch_time 5 non-null values\n",
106 | "inning 5 non-null values\n",
107 | "top_or_bottom 5 non-null values\n",
108 | "pitcher_name 5 non-null values\n",
109 | "hitter_name 5 non-null values\n",
110 | "pitch_type 5 non-null values\n",
111 | "x 5 non-null values\n",
112 | "y 5 non-null values\n",
113 | "start_speed 5 non-null values\n",
114 | "end_speed 5 non-null values\n",
115 | "sz_top 5 non-null values\n",
116 | "sz_bottom 5 non-null values\n",
117 | "pfx_x 5 non-null values\n",
118 | "pfx_z 5 non-null values\n",
119 | "px 5 non-null values\n",
120 | "pz 5 non-null values\n",
121 | "x0 5 non-null values\n",
122 | "y0 5 non-null values\n",
123 | "ax 5 non-null values\n",
124 | "ay 5 non-null values\n",
125 | "az 5 non-null values\n",
126 | "z0 5 non-null values\n",
127 | "vx0 5 non-null values\n",
128 | "vy0 5 non-null values\n",
129 | "vz0 5 non-null values\n",
130 | "break_y 5 non-null values\n",
131 | "break_angle 5 non-null values\n",
132 | "break_length 5 non-null values\n",
133 | "pitch_name 5 non-null values\n",
134 | "type_confidence 5 non-null values\n",
135 | "zone 5 non-null values\n",
136 | "nasty 5 non-null values\n",
137 | "spin_dir 5 non-null values\n",
138 | "spin_rate 5 non-null values\n",
139 | "comments 0 non-null values\n",
140 | "unk 0 non-null values\n",
141 | "dtypes: float64(28), int64(1), object(7)"
142 | ]
143 | }
144 | ],
145 | "prompt_number": 30
146 | },
147 | {
148 | "cell_type": "markdown",
149 | "metadata": {},
150 | "source": [
151 | "Let's limit this to a few less columns."
152 | ]
153 | },
154 | {
155 | "cell_type": "markdown",
156 | "metadata": {},
157 | "source": [
158 | "Cleaning the `pitch_name` column."
159 | ]
160 | },
161 | {
162 | "cell_type": "code",
163 | "collapsed": false,
164 | "input": [
165 | "lu = \"\"\"FA,Fastball\n",
166 | "FF,Fastball\n",
167 | "FT,Fastball\n",
168 | "FC,Cut fastball\n",
169 | "FS,Fastball (sinker|split-fingered)\n",
170 | "SI,Fastball (sinker|split-fingered)\n",
171 | "SF,Fastball (sinker|split-fingered)\n",
172 | "SL,Slider\n",
173 | "CH,Changeup\n",
174 | "CB,Curveball\n",
175 | "CU,Curveball\n",
176 | "KC,Curveball\n",
177 | "KN,Knuckleball\n",
178 | "EP,Eephus\n",
179 | "UN,Unidentified\n",
180 | "XX,Unidentified\n",
181 | "PO,Pitch out\n",
182 | "FO,Pitch out\"\"\".split('\\n')"
183 | ],
184 | "language": "python",
185 | "metadata": {},
186 | "outputs": [],
187 | "prompt_number": 31
188 | },
189 | {
190 | "cell_type": "code",
191 | "collapsed": false,
192 | "input": [
193 | "for row in lu:\n",
194 | " row = row.split(',')\n",
195 | " abbrv, name = row[0], row[1]\n",
196 | " df['pitch_name'] = df['pitch_name'].replace(abbrv, name)\n",
197 | "df['pitch_name'] = df['pitch_name']\n",
198 | "# df = df[df.pitch_name.isin(df.pitch_name.value_counts().head(8).index)]"
199 | ],
200 | "language": "python",
201 | "metadata": {},
202 | "outputs": [],
203 | "prompt_number": 32
204 | },
205 | {
206 | "cell_type": "code",
207 | "collapsed": false,
208 | "input": [
209 | "df.ix[:,:10].head()"
210 | ],
211 | "language": "python",
212 | "metadata": {},
213 | "outputs": [
214 | {
215 | "html": [
216 | "\n",
217 | "
\n",
218 | " \n",
219 | " \n",
220 | " | \n",
221 | " pitch_time | \n",
222 | " inning | \n",
223 | " top_or_bottom | \n",
224 | " pitcher_name | \n",
225 | " hitter_name | \n",
226 | " pitch_type | \n",
227 | " x | \n",
228 | " y | \n",
229 | " start_speed | \n",
230 | " end_speed | \n",
231 | "
\n",
232 | " \n",
233 | " \n",
234 | " \n",
235 | " 0 | \n",
236 | " 2013-10-01 20:07:43 -0400 | \n",
237 | " 1 | \n",
238 | " Top | \n",
239 | " Francisco Liriano | \n",
240 | " Shin-Soo Choo | \n",
241 | " B | \n",
242 | " 78.97 | \n",
243 | " 164.92 | \n",
244 | " 93.2 | \n",
245 | " 85.3 | \n",
246 | "
\n",
247 | " \n",
248 | " 1 | \n",
249 | " 2013-10-01 20:07:57 -0400 | \n",
250 | " 1 | \n",
251 | " Top | \n",
252 | " Francisco Liriano | \n",
253 | " Shin-Soo Choo | \n",
254 | " S | \n",
255 | " 82.40 | \n",
256 | " 131.24 | \n",
257 | " 93.4 | \n",
258 | " 85.6 | \n",
259 | "
\n",
260 | " \n",
261 | " 2 | \n",
262 | " 2013-10-01 20:08:12 -0400 | \n",
263 | " 1 | \n",
264 | " Top | \n",
265 | " Francisco Liriano | \n",
266 | " Shin-Soo Choo | \n",
267 | " S | \n",
268 | " 96.14 | \n",
269 | " 161.47 | \n",
270 | " 89.1 | \n",
271 | " 82.8 | \n",
272 | "
\n",
273 | " \n",
274 | " 3 | \n",
275 | " 2013-10-01 20:08:31 -0400 | \n",
276 | " 1 | \n",
277 | " Top | \n",
278 | " Francisco Liriano | \n",
279 | " Shin-Soo Choo | \n",
280 | " S | \n",
281 | " 106.44 | \n",
282 | " 163.19 | \n",
283 | " 90.0 | \n",
284 | " 83.3 | \n",
285 | "
\n",
286 | " \n",
287 | " 4 | \n",
288 | " 2013-10-01 20:09:09 -0400 | \n",
289 | " 1 | \n",
290 | " Top | \n",
291 | " Francisco Liriano | \n",
292 | " Ryan Ludwick | \n",
293 | " B | \n",
294 | " 163.95 | \n",
295 | " 194.28 | \n",
296 | " 87.7 | \n",
297 | " 81.6 | \n",
298 | "
\n",
299 | " \n",
300 | "
\n",
301 | "
"
302 | ],
303 | "metadata": {},
304 | "output_type": "pyout",
305 | "prompt_number": 33,
306 | "text": [
307 | " pitch_time inning top_or_bottom pitcher_name \\\n",
308 | "0 2013-10-01 20:07:43 -0400 1 Top Francisco Liriano \n",
309 | "1 2013-10-01 20:07:57 -0400 1 Top Francisco Liriano \n",
310 | "2 2013-10-01 20:08:12 -0400 1 Top Francisco Liriano \n",
311 | "3 2013-10-01 20:08:31 -0400 1 Top Francisco Liriano \n",
312 | "4 2013-10-01 20:09:09 -0400 1 Top Francisco Liriano \n",
313 | "\n",
314 | " hitter_name pitch_type x y start_speed end_speed \n",
315 | "0 Shin-Soo Choo B 78.97 164.92 93.2 85.3 \n",
316 | "1 Shin-Soo Choo S 82.40 131.24 93.4 85.6 \n",
317 | "2 Shin-Soo Choo S 96.14 161.47 89.1 82.8 \n",
318 | "3 Shin-Soo Choo S 106.44 163.19 90.0 83.3 \n",
319 | "4 Ryan Ludwick B 163.95 194.28 87.7 81.6 "
320 | ]
321 | }
322 | ],
323 | "prompt_number": 33
324 | },
325 | {
326 | "cell_type": "code",
327 | "collapsed": false,
328 | "input": [
329 | "df.ix[:,25:].head()"
330 | ],
331 | "language": "python",
332 | "metadata": {},
333 | "outputs": [
334 | {
335 | "html": [
336 | "\n",
337 | "
\n",
338 | " \n",
339 | " \n",
340 | " | \n",
341 | " break_y | \n",
342 | " break_angle | \n",
343 | " break_length | \n",
344 | " pitch_name | \n",
345 | " type_confidence | \n",
346 | " zone | \n",
347 | " nasty | \n",
348 | " spin_dir | \n",
349 | " spin_rate | \n",
350 | " comments | \n",
351 | " unk | \n",
352 | "
\n",
353 | " \n",
354 | " \n",
355 | " \n",
356 | " 0 | \n",
357 | " 23.8 | \n",
358 | " -41.3 | \n",
359 | " 6.3 | \n",
360 | " Fastball | \n",
361 | " 0.894 | \n",
362 | " 9 | \n",
363 | " 65 | \n",
364 | " 120.583 | \n",
365 | " 2541.561 | \n",
366 | " NaN | \n",
367 | " NaN | \n",
368 | "
\n",
369 | " \n",
370 | " 1 | \n",
371 | " 23.8 | \n",
372 | " -44.6 | \n",
373 | " 5.4 | \n",
374 | " Fastball | \n",
375 | " 0.895 | \n",
376 | " 12 | \n",
377 | " 62 | \n",
378 | " 128.371 | \n",
379 | " 2589.087 | \n",
380 | " NaN | \n",
381 | " NaN | \n",
382 | "
\n",
383 | " \n",
384 | " 2 | \n",
385 | " 23.8 | \n",
386 | " -10.4 | \n",
387 | " 5.8 | \n",
388 | " Slider | \n",
389 | " 0.931 | \n",
390 | " 8 | \n",
391 | " 32 | \n",
392 | " 148.073 | \n",
393 | " 1133.227 | \n",
394 | " NaN | \n",
395 | " NaN | \n",
396 | "
\n",
397 | " \n",
398 | " 3 | \n",
399 | " 23.8 | \n",
400 | " 2.6 | \n",
401 | " 6.8 | \n",
402 | " Slider | \n",
403 | " 0.926 | \n",
404 | " 8 | \n",
405 | " 34 | \n",
406 | " 189.793 | \n",
407 | " 430.593 | \n",
408 | " NaN | \n",
409 | " NaN | \n",
410 | "
\n",
411 | " \n",
412 | " 4 | \n",
413 | " 23.8 | \n",
414 | " -3.1 | \n",
415 | " 7.3 | \n",
416 | " Slider | \n",
417 | " 0.915 | \n",
418 | " 13 | \n",
419 | " 55 | \n",
420 | " 140.567 | \n",
421 | " 482.080 | \n",
422 | " NaN | \n",
423 | " NaN | \n",
424 | "
\n",
425 | " \n",
426 | "
\n",
427 | "
"
428 | ],
429 | "metadata": {},
430 | "output_type": "pyout",
431 | "prompt_number": 34,
432 | "text": [
433 | " break_y break_angle break_length pitch_name type_confidence zone \\\n",
434 | "0 23.8 -41.3 6.3 Fastball 0.894 9 \n",
435 | "1 23.8 -44.6 5.4 Fastball 0.895 12 \n",
436 | "2 23.8 -10.4 5.8 Slider 0.931 8 \n",
437 | "3 23.8 2.6 6.8 Slider 0.926 8 \n",
438 | "4 23.8 -3.1 7.3 Slider 0.915 13 \n",
439 | "\n",
440 | " nasty spin_dir spin_rate comments unk \n",
441 | "0 65 120.583 2541.561 NaN NaN \n",
442 | "1 62 128.371 2589.087 NaN NaN \n",
443 | "2 32 148.073 1133.227 NaN NaN \n",
444 | "3 34 189.793 430.593 NaN NaN \n",
445 | "4 55 140.567 482.080 NaN NaN "
446 | ]
447 | }
448 | ],
449 | "prompt_number": 34
450 | },
451 | {
452 | "cell_type": "code",
453 | "collapsed": false,
454 | "input": [
455 | "df.ix[:,25:].head()"
456 | ],
457 | "language": "python",
458 | "metadata": {},
459 | "outputs": [
460 | {
461 | "html": [
462 | "\n",
463 | "
\n",
464 | " \n",
465 | " \n",
466 | " | \n",
467 | " break_y | \n",
468 | " break_angle | \n",
469 | " break_length | \n",
470 | " pitch_name | \n",
471 | " type_confidence | \n",
472 | " zone | \n",
473 | " nasty | \n",
474 | " spin_dir | \n",
475 | " spin_rate | \n",
476 | " comments | \n",
477 | " unk | \n",
478 | "
\n",
479 | " \n",
480 | " \n",
481 | " \n",
482 | " 0 | \n",
483 | " 23.8 | \n",
484 | " -41.3 | \n",
485 | " 6.3 | \n",
486 | " Fastball | \n",
487 | " 0.894 | \n",
488 | " 9 | \n",
489 | " 65 | \n",
490 | " 120.583 | \n",
491 | " 2541.561 | \n",
492 | " NaN | \n",
493 | " NaN | \n",
494 | "
\n",
495 | " \n",
496 | " 1 | \n",
497 | " 23.8 | \n",
498 | " -44.6 | \n",
499 | " 5.4 | \n",
500 | " Fastball | \n",
501 | " 0.895 | \n",
502 | " 12 | \n",
503 | " 62 | \n",
504 | " 128.371 | \n",
505 | " 2589.087 | \n",
506 | " NaN | \n",
507 | " NaN | \n",
508 | "
\n",
509 | " \n",
510 | " 2 | \n",
511 | " 23.8 | \n",
512 | " -10.4 | \n",
513 | " 5.8 | \n",
514 | " Slider | \n",
515 | " 0.931 | \n",
516 | " 8 | \n",
517 | " 32 | \n",
518 | " 148.073 | \n",
519 | " 1133.227 | \n",
520 | " NaN | \n",
521 | " NaN | \n",
522 | "
\n",
523 | " \n",
524 | " 3 | \n",
525 | " 23.8 | \n",
526 | " 2.6 | \n",
527 | " 6.8 | \n",
528 | " Slider | \n",
529 | " 0.926 | \n",
530 | " 8 | \n",
531 | " 34 | \n",
532 | " 189.793 | \n",
533 | " 430.593 | \n",
534 | " NaN | \n",
535 | " NaN | \n",
536 | "
\n",
537 | " \n",
538 | " 4 | \n",
539 | " 23.8 | \n",
540 | " -3.1 | \n",
541 | " 7.3 | \n",
542 | " Slider | \n",
543 | " 0.915 | \n",
544 | " 13 | \n",
545 | " 55 | \n",
546 | " 140.567 | \n",
547 | " 482.080 | \n",
548 | " NaN | \n",
549 | " NaN | \n",
550 | "
\n",
551 | " \n",
552 | "
\n",
553 | "
"
554 | ],
555 | "metadata": {},
556 | "output_type": "pyout",
557 | "prompt_number": 35,
558 | "text": [
559 | " break_y break_angle break_length pitch_name type_confidence zone \\\n",
560 | "0 23.8 -41.3 6.3 Fastball 0.894 9 \n",
561 | "1 23.8 -44.6 5.4 Fastball 0.895 12 \n",
562 | "2 23.8 -10.4 5.8 Slider 0.931 8 \n",
563 | "3 23.8 2.6 6.8 Slider 0.926 8 \n",
564 | "4 23.8 -3.1 7.3 Slider 0.915 13 \n",
565 | "\n",
566 | " nasty spin_dir spin_rate comments unk \n",
567 | "0 65 120.583 2541.561 NaN NaN \n",
568 | "1 62 128.371 2589.087 NaN NaN \n",
569 | "2 32 148.073 1133.227 NaN NaN \n",
570 | "3 34 189.793 430.593 NaN NaN \n",
571 | "4 55 140.567 482.080 NaN NaN "
572 | ]
573 | }
574 | ],
575 | "prompt_number": 35
576 | },
577 | {
578 | "cell_type": "code",
579 | "collapsed": false,
580 | "input": [
581 | "df = df[df.pitch_name.isin([\"IN\", \"Pitch out\", \"SC\"])==False]\n",
582 | "df = df[df.pitch_name.isnull()==False]"
583 | ],
584 | "language": "python",
585 | "metadata": {},
586 | "outputs": [],
587 | "prompt_number": 37
588 | },
589 | {
590 | "cell_type": "code",
591 | "collapsed": false,
592 | "input": [
593 | "df.to_csv(\"./baseball-pitches-clean.csv\", index=False)"
594 | ],
595 | "language": "python",
596 | "metadata": {},
597 | "outputs": [],
598 | "prompt_number": 38
599 | }
600 | ],
601 | "metadata": {}
602 | }
603 | ]
604 | }
--------------------------------------------------------------------------------
/notebooks/01 - The Basics - The API, Datasets, Your First ggplot.ipynb:
--------------------------------------------------------------------------------
1 | {
2 | "metadata": {
3 | "name": ""
4 | },
5 | "nbformat": 3,
6 | "nbformat_minor": 0,
7 | "worksheets": [
8 | {
9 | "cells": [
10 | {
11 | "cell_type": "code",
12 | "collapsed": false,
13 | "input": [
14 | "# import * is a personal choice\n",
15 | "from ggplot import *\n",
16 | "# our trusty old friends\n",
17 | "import pandas as pd\n",
18 | "import numpy as np"
19 | ],
20 | "language": "python",
21 | "metadata": {},
22 | "outputs": [],
23 | "prompt_number": 2
24 | },
25 | {
26 | "cell_type": "code",
27 | "collapsed": false,
28 | "input": [
29 | "%matplotlib inline"
30 | ],
31 | "language": "python",
32 | "metadata": {},
33 | "outputs": [],
34 | "prompt_number": 1
35 | },
36 | {
37 | "cell_type": "markdown",
38 | "metadata": {},
39 | "source": [
40 | "## Built in datasets"
41 | ]
42 | },
43 | {
44 | "cell_type": "code",
45 | "collapsed": false,
46 | "input": [
47 | "meat.head()"
48 | ],
49 | "language": "python",
50 | "metadata": {},
51 | "outputs": [
52 | {
53 | "html": [
54 | "\n",
55 | "
\n",
56 | " \n",
57 | " \n",
58 | " | \n",
59 | " date | \n",
60 | " beef | \n",
61 | " veal | \n",
62 | " pork | \n",
63 | " lamb_and_mutton | \n",
64 | " broilers | \n",
65 | " other_chicken | \n",
66 | " turkey | \n",
67 | "
\n",
68 | " \n",
69 | " \n",
70 | " \n",
71 | " 0 | \n",
72 | " 1944-01-01 | \n",
73 | " 751 | \n",
74 | " 85 | \n",
75 | " 1280 | \n",
76 | " 89 | \n",
77 | " NaN | \n",
78 | " NaN | \n",
79 | " NaN | \n",
80 | "
\n",
81 | " \n",
82 | " 1 | \n",
83 | " 1944-02-01 | \n",
84 | " 713 | \n",
85 | " 77 | \n",
86 | " 1169 | \n",
87 | " 72 | \n",
88 | " NaN | \n",
89 | " NaN | \n",
90 | " NaN | \n",
91 | "
\n",
92 | " \n",
93 | " 2 | \n",
94 | " 1944-03-01 | \n",
95 | " 741 | \n",
96 | " 90 | \n",
97 | " 1128 | \n",
98 | " 75 | \n",
99 | " NaN | \n",
100 | " NaN | \n",
101 | " NaN | \n",
102 | "
\n",
103 | " \n",
104 | " 3 | \n",
105 | " 1944-04-01 | \n",
106 | " 650 | \n",
107 | " 89 | \n",
108 | " 978 | \n",
109 | " 66 | \n",
110 | " NaN | \n",
111 | " NaN | \n",
112 | " NaN | \n",
113 | "
\n",
114 | " \n",
115 | " 4 | \n",
116 | " 1944-05-01 | \n",
117 | " 681 | \n",
118 | " 106 | \n",
119 | " 1029 | \n",
120 | " 78 | \n",
121 | " NaN | \n",
122 | " NaN | \n",
123 | " NaN | \n",
124 | "
\n",
125 | " \n",
126 | "
\n",
127 | "
5 rows \u00d7 8 columns
\n",
128 | "
"
129 | ],
130 | "metadata": {},
131 | "output_type": "pyout",
132 | "prompt_number": 3,
133 | "text": [
134 | " date beef veal pork lamb_and_mutton broilers other_chicken \\\n",
135 | "0 1944-01-01 751 85 1280 89 NaN NaN \n",
136 | "1 1944-02-01 713 77 1169 72 NaN NaN \n",
137 | "2 1944-03-01 741 90 1128 75 NaN NaN \n",
138 | "3 1944-04-01 650 89 978 66 NaN NaN \n",
139 | "4 1944-05-01 681 106 1029 78 NaN NaN \n",
140 | "\n",
141 | " turkey \n",
142 | "0 NaN \n",
143 | "1 NaN \n",
144 | "2 NaN \n",
145 | "3 NaN \n",
146 | "4 NaN \n",
147 | "\n",
148 | "[5 rows x 8 columns]"
149 | ]
150 | }
151 | ],
152 | "prompt_number": 3
153 | },
154 | {
155 | "cell_type": "code",
156 | "collapsed": false,
157 | "input": [
158 | "diamonds.head()"
159 | ],
160 | "language": "python",
161 | "metadata": {},
162 | "outputs": [
163 | {
164 | "html": [
165 | "\n",
166 | "
\n",
167 | " \n",
168 | " \n",
169 | " | \n",
170 | " carat | \n",
171 | " cut | \n",
172 | " color | \n",
173 | " clarity | \n",
174 | " depth | \n",
175 | " table | \n",
176 | " price | \n",
177 | " x | \n",
178 | " y | \n",
179 | " z | \n",
180 | "
\n",
181 | " \n",
182 | " \n",
183 | " \n",
184 | " 0 | \n",
185 | " 0.23 | \n",
186 | " Ideal | \n",
187 | " E | \n",
188 | " SI2 | \n",
189 | " 61.5 | \n",
190 | " 55 | \n",
191 | " 326 | \n",
192 | " 3.95 | \n",
193 | " 3.98 | \n",
194 | " 2.43 | \n",
195 | "
\n",
196 | " \n",
197 | " 1 | \n",
198 | " 0.21 | \n",
199 | " Premium | \n",
200 | " E | \n",
201 | " SI1 | \n",
202 | " 59.8 | \n",
203 | " 61 | \n",
204 | " 326 | \n",
205 | " 3.89 | \n",
206 | " 3.84 | \n",
207 | " 2.31 | \n",
208 | "
\n",
209 | " \n",
210 | " 2 | \n",
211 | " 0.23 | \n",
212 | " Good | \n",
213 | " E | \n",
214 | " VS1 | \n",
215 | " 56.9 | \n",
216 | " 65 | \n",
217 | " 327 | \n",
218 | " 4.05 | \n",
219 | " 4.07 | \n",
220 | " 2.31 | \n",
221 | "
\n",
222 | " \n",
223 | " 3 | \n",
224 | " 0.29 | \n",
225 | " Premium | \n",
226 | " I | \n",
227 | " VS2 | \n",
228 | " 62.4 | \n",
229 | " 58 | \n",
230 | " 334 | \n",
231 | " 4.20 | \n",
232 | " 4.23 | \n",
233 | " 2.63 | \n",
234 | "
\n",
235 | " \n",
236 | " 4 | \n",
237 | " 0.31 | \n",
238 | " Good | \n",
239 | " J | \n",
240 | " SI2 | \n",
241 | " 63.3 | \n",
242 | " 58 | \n",
243 | " 335 | \n",
244 | " 4.34 | \n",
245 | " 4.35 | \n",
246 | " 2.75 | \n",
247 | "
\n",
248 | " \n",
249 | "
\n",
250 | "
5 rows \u00d7 10 columns
\n",
251 | "
"
252 | ],
253 | "metadata": {},
254 | "output_type": "pyout",
255 | "prompt_number": 4,
256 | "text": [
257 | " carat cut color clarity depth table price x y z\n",
258 | "0 0.23 Ideal E SI2 61.5 55 326 3.95 3.98 2.43\n",
259 | "1 0.21 Premium E SI1 59.8 61 326 3.89 3.84 2.31\n",
260 | "2 0.23 Good E VS1 56.9 65 327 4.05 4.07 2.31\n",
261 | "3 0.29 Premium I VS2 62.4 58 334 4.20 4.23 2.63\n",
262 | "4 0.31 Good J SI2 63.3 58 335 4.34 4.35 2.75\n",
263 | "\n",
264 | "[5 rows x 10 columns]"
265 | ]
266 | }
267 | ],
268 | "prompt_number": 4
269 | },
270 | {
271 | "cell_type": "code",
272 | "collapsed": false,
273 | "input": [
274 | "mtcars.head()"
275 | ],
276 | "language": "python",
277 | "metadata": {},
278 | "outputs": [
279 | {
280 | "html": [
281 | "\n",
282 | "
\n",
283 | " \n",
284 | " \n",
285 | " | \n",
286 | " name | \n",
287 | " mpg | \n",
288 | " cyl | \n",
289 | " disp | \n",
290 | " hp | \n",
291 | " drat | \n",
292 | " wt | \n",
293 | " qsec | \n",
294 | " vs | \n",
295 | " am | \n",
296 | " gear | \n",
297 | " carb | \n",
298 | "
\n",
299 | " \n",
300 | " \n",
301 | " \n",
302 | " 0 | \n",
303 | " Mazda RX4 | \n",
304 | " 21.0 | \n",
305 | " 6 | \n",
306 | " 160 | \n",
307 | " 110 | \n",
308 | " 3.90 | \n",
309 | " 2.620 | \n",
310 | " 16.46 | \n",
311 | " 0 | \n",
312 | " 1 | \n",
313 | " 4 | \n",
314 | " 4 | \n",
315 | "
\n",
316 | " \n",
317 | " 1 | \n",
318 | " Mazda RX4 Wag | \n",
319 | " 21.0 | \n",
320 | " 6 | \n",
321 | " 160 | \n",
322 | " 110 | \n",
323 | " 3.90 | \n",
324 | " 2.875 | \n",
325 | " 17.02 | \n",
326 | " 0 | \n",
327 | " 1 | \n",
328 | " 4 | \n",
329 | " 4 | \n",
330 | "
\n",
331 | " \n",
332 | " 2 | \n",
333 | " Datsun 710 | \n",
334 | " 22.8 | \n",
335 | " 4 | \n",
336 | " 108 | \n",
337 | " 93 | \n",
338 | " 3.85 | \n",
339 | " 2.320 | \n",
340 | " 18.61 | \n",
341 | " 1 | \n",
342 | " 1 | \n",
343 | " 4 | \n",
344 | " 1 | \n",
345 | "
\n",
346 | " \n",
347 | " 3 | \n",
348 | " Hornet 4 Drive | \n",
349 | " 21.4 | \n",
350 | " 6 | \n",
351 | " 258 | \n",
352 | " 110 | \n",
353 | " 3.08 | \n",
354 | " 3.215 | \n",
355 | " 19.44 | \n",
356 | " 1 | \n",
357 | " 0 | \n",
358 | " 3 | \n",
359 | " 1 | \n",
360 | "
\n",
361 | " \n",
362 | " 4 | \n",
363 | " Hornet Sportabout | \n",
364 | " 18.7 | \n",
365 | " 8 | \n",
366 | " 360 | \n",
367 | " 175 | \n",
368 | " 3.15 | \n",
369 | " 3.440 | \n",
370 | " 17.02 | \n",
371 | " 0 | \n",
372 | " 0 | \n",
373 | " 3 | \n",
374 | " 2 | \n",
375 | "
\n",
376 | " \n",
377 | "
\n",
378 | "
5 rows \u00d7 12 columns
\n",
379 | "
"
380 | ],
381 | "metadata": {},
382 | "output_type": "pyout",
383 | "prompt_number": 5,
384 | "text": [
385 | " name mpg cyl disp hp drat wt qsec vs am gear \\\n",
386 | "0 Mazda RX4 21.0 6 160 110 3.90 2.620 16.46 0 1 4 \n",
387 | "1 Mazda RX4 Wag 21.0 6 160 110 3.90 2.875 17.02 0 1 4 \n",
388 | "2 Datsun 710 22.8 4 108 93 3.85 2.320 18.61 1 1 4 \n",
389 | "3 Hornet 4 Drive 21.4 6 258 110 3.08 3.215 19.44 1 0 3 \n",
390 | "4 Hornet Sportabout 18.7 8 360 175 3.15 3.440 17.02 0 0 3 \n",
391 | "\n",
392 | " carb \n",
393 | "0 4 \n",
394 | "1 4 \n",
395 | "2 1 \n",
396 | "3 1 \n",
397 | "4 2 \n",
398 | "\n",
399 | "[5 rows x 12 columns]"
400 | ]
401 | }
402 | ],
403 | "prompt_number": 5
404 | },
405 | {
406 | "cell_type": "code",
407 | "collapsed": false,
408 | "input": [
409 | "pageviews.head()"
410 | ],
411 | "language": "python",
412 | "metadata": {},
413 | "outputs": [
414 | {
415 | "html": [
416 | "\n",
417 | "
\n",
418 | " \n",
419 | " \n",
420 | " | \n",
421 | " date_hour | \n",
422 | " pageviews | \n",
423 | "
\n",
424 | " \n",
425 | " \n",
426 | " \n",
427 | " 0 | \n",
428 | " 2013-02-11 21:00:00 | \n",
429 | " 8860.982383 | \n",
430 | "
\n",
431 | " \n",
432 | " 1 | \n",
433 | " 2013-02-11 22:00:00 | \n",
434 | " 8637.474753 | \n",
435 | "
\n",
436 | " \n",
437 | " 2 | \n",
438 | " 2013-02-11 23:00:00 | \n",
439 | " 9020.593099 | \n",
440 | "
\n",
441 | " \n",
442 | " 3 | \n",
443 | " 2013-02-12 00:00:00 | \n",
444 | " 8437.500380 | \n",
445 | "
\n",
446 | " \n",
447 | " 4 | \n",
448 | " 2013-02-12 01:00:00 | \n",
449 | " 9157.399672 | \n",
450 | "
\n",
451 | " \n",
452 | "
\n",
453 | "
"
454 | ],
455 | "metadata": {},
456 | "output_type": "pyout",
457 | "prompt_number": 7,
458 | "text": [
459 | " date_hour pageviews\n",
460 | "0 2013-02-11 21:00:00 8860.982383\n",
461 | "1 2013-02-11 22:00:00 8637.474753\n",
462 | "2 2013-02-11 23:00:00 9020.593099\n",
463 | "3 2013-02-12 00:00:00 8437.500380\n",
464 | "4 2013-02-12 01:00:00 9157.399672"
465 | ]
466 | }
467 | ],
468 | "prompt_number": 7
469 | },
470 | {
471 | "cell_type": "markdown",
472 | "metadata": {},
473 | "source": [
474 | "## The API\n",
475 | "\n",
476 | "### `ggplot`\n",
477 | "`ggplot`'s API revolves around the `ggplot` class. It's class that behaves much more like a function (you don't really operate on `ggplot` methods). "
478 | ]
479 | },
480 | {
481 | "cell_type": "code",
482 | "collapsed": false,
483 | "input": [
484 | "?ggplot"
485 | ],
486 | "language": "python",
487 | "metadata": {},
488 | "outputs": [],
489 | "prompt_number": 9
490 | },
491 | {
492 | "cell_type": "markdown",
493 | "metadata": {},
494 | "source": [
495 | "ggplots take 2 arguments: a data frame and accompanying \"aesthetics\" or `aes`. These are equivalent."
496 | ]
497 | },
498 | {
499 | "cell_type": "code",
500 | "collapsed": false,
501 | "input": [
502 | "p = ggplot(aes(x='wt'), data=mtcars)"
503 | ],
504 | "language": "python",
505 | "metadata": {},
506 | "outputs": [],
507 | "prompt_number": 6
508 | },
509 | {
510 | "cell_type": "code",
511 | "collapsed": false,
512 | "input": [
513 | "p = ggplot(mtcars, aes(x='wt'))"
514 | ],
515 | "language": "python",
516 | "metadata": {},
517 | "outputs": [],
518 | "prompt_number": 7
519 | },
520 | {
521 | "cell_type": "markdown",
522 | "metadata": {},
523 | "source": [
524 | "A ggplot is a \"base layer\". It won't create any aesthetics but think of it as a canvas. Watch what happens when you render it."
525 | ]
526 | },
527 | {
528 | "cell_type": "code",
529 | "collapsed": false,
530 | "input": [
531 | "p"
532 | ],
533 | "language": "python",
534 | "metadata": {},
535 | "outputs": [
536 | {
537 | "metadata": {},
538 | "output_type": "display_data",
539 | "png": "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\n1rVaLU6dOhXd3d0xMTERv/rVr2y9zaxn57eu+81vfhN33nlnm07KjVrP1leuXFl+m9v+/v6Ym5tr\n44nZqPVs/cILL8Ttt98e999/f8zNzcWPfvSjuOeee6JcLrfx5GTdd9998dGPfjSeeuqpd/38Rpps\n1V/js1HeArE41rP1+973vuju7o6I61vX6/V2HJUbsJ6dIyJ+//vfx4EDB2LPnj1tOCWbYT1bv/TS\nS/HBD35w+Z3K7L09rWfrvr6+WFhYiIiIhYWF6OnpEY/b0P79+5f/O/xuNtJkWxKQ7/YWiDMzMyuu\n+V9vgcj2sp6t3+4Pf/jDO/5WPze/9excr9fj5Zdfjo985COtPh6baD1bT01NxZUrV+JnP/tZ/PSn\nP13+XcBsL+vZemRkJP75z3/G97///fjJT34Sn/vc51p9TFpgI022JQF5o2+ByPaR2frVV1+NP/7x\nj/HZz352C0/EVljPzmfOnIn7778/SqVS+Lt529d6tr527Vr84x//iC9/+cvxla98JcbHx+Nf//pX\nC07HZlrP1r/73e/itttui+9+97vxzW9+M5577rnl70hSbFvyM5A3+haIbB/r3fH111+PX/7yl3Hy\n5Mno6elp5RHZBOvZ+e9//3s88cQTERHx5ptvxsWLF6OjoyPuvvvulp6VG7Oerfv7+2P37t3R2dkZ\nnZ2dsX///nj99dfjlltuafVxuQHr2fq1116LT3/60xERyy93v/HGG/He9763pWdla22kybbkO5A3\n+haIbB/r2frf//53/OIXv4jPf/7z/gOzTa1n50cffXT5nwMHDsTx48fF4za03v///utf/xqNRiOu\nXr0ak5OT3qp2G1rP1rfeemv8+c9/jojr75v8xhtvRK1Wa8dx2UIbabIt+z2Qb/1qgLfeAvFTn/rU\nirdAjIh47rnn4uLFi8tvgbhv376tOApbbK2tn3nmmbhw4cLyz9p0dHTEN77xjXYemQ1Yz7/Tb3n6\n6afjrrvu8mt8tqn1bP3888/H//3f/0WpVIqRkZH42Mc+1s4js0FrbT03NxfPPPNMXL58OZrNZhw+\nfDjuueeeNp+arCeeeCL+8pe/xJtvvhm9vb3xmc98JhqNRkRsvMn8InEAAFK25CVsAAB2LgEJAECK\ngAQAIEVAAgCQIiABAEgRkAAApAhIAABS/h/62YH95FMTSgAAAABJRU5ErkJggg==\n",
540 | "text": [
541 | ""
542 | ]
543 | },
544 | {
545 | "metadata": {},
546 | "output_type": "pyout",
547 | "prompt_number": 8,
548 | "text": [
549 | ""
550 | ]
551 | }
552 | ],
553 | "prompt_number": 8
554 | },
555 | {
556 | "cell_type": "markdown",
557 | "metadata": {},
558 | "source": [
559 | "### `aes`\n",
560 | "Aesthetics or `aes` define how ggplot with extract data from your data frame and render it. Think of it as the instructions for creating x, y, color, etc. components.\n",
561 | "\n",
562 | "`aes` is just a dictionary with keys being an aesthetic property and values being strings or formulas--for more on formulas read [this]( http://patsy.readthedocs.org/en/v0.1.0/formulas.html)--relating to data in your data frame."
563 | ]
564 | },
565 | {
566 | "cell_type": "code",
567 | "collapsed": false,
568 | "input": [
569 | "aes(x='date', y='price')"
570 | ],
571 | "language": "python",
572 | "metadata": {},
573 | "outputs": [
574 | {
575 | "metadata": {},
576 | "output_type": "pyout",
577 | "prompt_number": 9,
578 | "text": [
579 | "{'y': 'price', 'x': 'date'}"
580 | ]
581 | }
582 | ],
583 | "prompt_number": 9
584 | },
585 | {
586 | "cell_type": "code",
587 | "collapsed": false,
588 | "input": [
589 | "# shorthand\n",
590 | "aes('date', 'price')"
591 | ],
592 | "language": "python",
593 | "metadata": {},
594 | "outputs": [
595 | {
596 | "metadata": {},
597 | "output_type": "pyout",
598 | "prompt_number": 10,
599 | "text": [
600 | "{u'y': 'price', u'x': 'date'}"
601 | ]
602 | }
603 | ],
604 | "prompt_number": 10
605 | },
606 | {
607 | "cell_type": "code",
608 | "collapsed": false,
609 | "input": [
610 | "# shorthand\n",
611 | "aes('date', 'price', 'name')"
612 | ],
613 | "language": "python",
614 | "metadata": {},
615 | "outputs": [
616 | {
617 | "metadata": {},
618 | "output_type": "pyout",
619 | "prompt_number": 11,
620 | "text": [
621 | "{u'y': 'price', u'x': 'date', u'color': 'name'}"
622 | ]
623 | }
624 | ],
625 | "prompt_number": 11
626 | },
627 | {
628 | "cell_type": "code",
629 | "collapsed": false,
630 | "input": [
631 | "# formula\n",
632 | "aes(x='date', y='price', color='date * price', shape='factor(name)')"
633 | ],
634 | "language": "python",
635 | "metadata": {},
636 | "outputs": [
637 | {
638 | "metadata": {},
639 | "output_type": "pyout",
640 | "prompt_number": 12,
641 | "text": [
642 | "{'color': 'date * price', 'y': 'price', 'shape': 'factor(name)', 'x': 'date'}"
643 | ]
644 | }
645 | ],
646 | "prompt_number": 12
647 | },
648 | {
649 | "cell_type": "markdown",
650 | "metadata": {},
651 | "source": [
652 | "## Your first `ggplot`\n",
653 | "\n",
654 | "So taking everything that we've learned, let's use the `mtcars` dataset to plot the relationship between car weight (`wt`) and miles per gallon (`mpg`). First create a `ggplot` object with the proper `aes` and name it `p`."
655 | ]
656 | },
657 | {
658 | "cell_type": "code",
659 | "collapsed": false,
660 | "input": [
661 | "p = ggplot(aes(x='wt', y='mpg'), data=mtcars)\n",
662 | "p"
663 | ],
664 | "language": "python",
665 | "metadata": {},
666 | "outputs": [
667 | {
668 | "metadata": {},
669 | "output_type": "display_data",
670 | "png": "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\n1rVaLU6dOhXd3d0xMTERv/rVr2y9zaxn57eu+81vfhN33nlnm07KjVrP1leuXFl+m9v+/v6Ym5tr\n44nZqPVs/cILL8Ttt98e999/f8zNzcWPfvSjuOeee6JcLrfx5GTdd9998dGPfjSeeuqpd/38Rpps\n1V/js1HeArE41rP1+973vuju7o6I61vX6/V2HJUbsJ6dIyJ+//vfx4EDB2LPnj1tOCWbYT1bv/TS\nS/HBD35w+Z3K7L09rWfrvr6+WFhYiIiIhYWF6OnpEY/b0P79+5f/O/xuNtJkWxKQ7/YWiDMzMyuu\n+V9vgcj2sp6t3+4Pf/jDO/5WPze/9excr9fj5Zdfjo985COtPh6baD1bT01NxZUrV+JnP/tZ/PSn\nP13+XcBsL+vZemRkJP75z3/G97///fjJT34Sn/vc51p9TFpgI022JQF5o2+ByPaR2frVV1+NP/7x\nj/HZz352C0/EVljPzmfOnIn7778/SqVS+Lt529d6tr527Vr84x//iC9/+cvxla98JcbHx+Nf//pX\nC07HZlrP1r/73e/itttui+9+97vxzW9+M5577rnl70hSbFvyM5A3+haIbB/r3fH111+PX/7yl3Hy\n5Mno6elp5RHZBOvZ+e9//3s88cQTERHx5ptvxsWLF6OjoyPuvvvulp6VG7Oerfv7+2P37t3R2dkZ\nnZ2dsX///nj99dfjlltuafVxuQHr2fq1116LT3/60xERyy93v/HGG/He9763pWdla22kybbkO5A3\n+haIbB/r2frf//53/OIXv4jPf/7z/gOzTa1n50cffXT5nwMHDsTx48fF4za03v///utf/xqNRiOu\nXr0ak5OT3qp2G1rP1rfeemv8+c9/jojr75v8xhtvRK1Wa8dx2UIbabIt+z2Qb/1qgLfeAvFTn/rU\nirdAjIh47rnn4uLFi8tvgbhv376tOApbbK2tn3nmmbhw4cLyz9p0dHTEN77xjXYemQ1Yz7/Tb3n6\n6afjrrvu8mt8tqn1bP3888/H//3f/0WpVIqRkZH42Mc+1s4js0FrbT03NxfPPPNMXL58OZrNZhw+\nfDjuueeeNp+arCeeeCL+8pe/xJtvvhm9vb3xmc98JhqNRkRsvMn8InEAAFK25CVsAAB2LgEJAECK\ngAQAIEVAAgCQIiABAEgRkAAApAhIAABS/h/62YH95FMTSgAAAABJRU5ErkJggg==\n",
671 | "text": [
672 | ""
673 | ]
674 | },
675 | {
676 | "metadata": {},
677 | "output_type": "pyout",
678 | "prompt_number": 30,
679 | "text": [
680 | ""
681 | ]
682 | }
683 | ],
684 | "prompt_number": 30
685 | },
686 | {
687 | "cell_type": "markdown",
688 | "metadata": {},
689 | "source": [
690 | "Now let's (quite literally) add a scatterplot (`geom_point`) to our plot. We'll get into more detail on how this works later."
691 | ]
692 | },
693 | {
694 | "cell_type": "code",
695 | "collapsed": false,
696 | "input": [
697 | "p + geom_point()"
698 | ],
699 | "language": "python",
700 | "metadata": {},
701 | "outputs": [
702 | {
703 | "metadata": {},
704 | "output_type": "display_data",
705 | "png": "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\nLDFrp3DanCVm7SQul6tV27Xqt2D+/Pn6xS9+od/85jfq0aOH9u7dqzvvvFO33367otFofDvTxTM9\nPV3V1dV8SkpyXq9XoVBItbW1zDqJOXXOErN2CqfNWWLWTuL1elu1XasOnbemQLpcLkUikVa96Klg\nd3zy49CLMzh1zhKzdgqnzVli1k6S0EPnZWVl37mLtBU9FQAAAA7UqqIZCoX0hz/8QR988IFqamri\n610ul9atW2csHAAAANqvVhXNmTNnKhqN6vzzz1d6enp8fWtPBAUAAIDztKpovvfee/riiy+OuwsH\nAAAA8F1a9TXxkSNHatu2baazAAAAIIm0ao/mkiVLNGnSJI0YMUI5OTnxLwC5XC7ddtttRgMCAACg\nfWpV0Zw3b54OHDigzz//XFVVVaYzAUktEomooqJCmZmZnI4CAEhqrSqay5Yt0/bt29WtWzfTeYCk\ntnPnTl1zzTWqqKhQIBDQvHnzNHnyZLtjAQBgRKvO0ezdu3errwAP4Lvdcsst+vTTT3X48GHt2rVL\nd999tyU3OmiNTz/9VBdeeKGmTJmi//7v/24zuU5FU1OT/uu//ktTpkzRzJkztXPnTrsjAYCjtGqP\n5uWXX65p06bp+uuvV05OToufjR071kgwIBl98zq0klRXV6fa2loFg0GbEv0jx5w5c7Rjxw5J0scf\nf6z09HT95je/sTXXqbr11lu1bNmy+HnlV199tV577TU+OAOARVpVNB999FG5XC7NmzfvuJ/t2rUr\n4aGAZJWXl6ePPvoovty1a1cFAgEbE31t9+7dOnjwYHw5HA7r448/tjFRYnz22Wct7l72+eef69Ch\nQzr99NNtTAUAztGqorl7927DMQBnePDBB+X1elVWVqaOHTvqgQceaBM3PujatasyMzNVV1cXX5eV\nlWVjosT49p7iQCCgTp062ZQGAJynVUUTQGKkp6fr97//vd0xjpOVlaXrrrtOTzzxhBoaGtSjRw/d\nfffddsc6Zffff7+uuOIKHTp0SB06dNANN9ygjIwMu2MBgGNQNIF2KhKJ6K677tJHH32krKws3XXX\nXae0F/Lyyy/XxRdfrNraWmVmZp50T+uaNWv07LPPyuVy6T//8z81fPjw7/3apuTk5Gjt2rX66quv\nFAgElJqaanckAHAUiibQTv3617/W0qVLFQ6HJUkHDhzQmjVrTulQfFpaWquu7blhwwbdeuut+vLL\nLyVJO3bs0LJly9S7d+/v/dqmuFwuDpcDgE1adXkjAG3Phx9+GC+ZkrR//3599dVXlrz2ihUr4iVT\nkg4ePKi1a9da8toAgPaDogm0U+np6cct+/1+S167W7duLfacpqamqkePHpa8NgCg/aBoAu3UHXfc\nob59+6pDhw7q1q2b5syZY9ktLX/5y19q5MiRCgQCCoVCmjBhgs477zxLXhsA0H5wjibQTvXv31+v\nvvqqdu3apZycHHXu3Nmy105LS9Pzzz+vnTt3yuPxqFevXm3iMk0AgLaFogm0Yx06dNCZZ55py2u7\n3W7l5+fb8toAgPaBQ+cAAAAwgqIJAAAAIyiaAAAAMIKiCQAAACMs+zLQ0aNHVVxcrNraWknSkCFD\ndPbZZ6uurk4rVqzQkSNHFAqFNHPmTPl8PqtiAQAAwBDLiqbb7dbEiROVm5urxsZGLVq0SH369NEH\nH3ygvLw8jRo1Shs2bNCGDRs0fvx4q2IBAADAEMsOnQcCAeXm5kr6+hp8nTt3VlVVlbZv366zzjpL\nkjRw4EBt27bNqkgAAAAwyJbraFZWVqq8vFynnXaaamtr47fN8/v98UPrVVVVqqmpafE4v98vj8dZ\nl/5MSUmR1+u1O4aljs2YWSc3p85ZYtZO4bQ5S8zaSVo7Y8t/ExobG7Vs2TKde+65x90u75t3Ftm4\ncaNKSkpa/LywsFBjxoyxJCfsl5mZaXcEWIA5Owezdg5mjWMsLZqRSETLli3TgAED1L9/f0lSRkaG\nqqurFQgEVF1drYyMDElff1mooKCgxeP9fr8qKysVDoetjG2rtLQ0NTY22h3DUh6PR5mZmczaYuXl\n5QqHw+revbslt5N06pwl+2dtNafO2mlzlpi1kxyb9Um3syCLJCkWi2n16tXKzs7WiBEj4usLCgq0\nZcsWjRo1Sps3b1a/fv0kScFgUMFg8LjnqaioUHNzs1WxbefxeBz1fr8pHA476r3bNetYLKbrr79e\nb775pmKxmAYOHKgnn3zSskNfTpuz5Ny/a6fN2qlzlpg1/sGyorl37159+OGHysnJ0YIFCyRJ48aN\n06hRo7R8+XJt2rQpfnkjANZZs2aNXnnllfin8ZKSEi1YsEDXXXedzckAAO2dZUWzZ8+emj9//gl/\nNmvWLKtiAPiWnTt3tjjkE4lEVFZWZmMiAECy4M5AgMNNnjxZXbt2jS936tRJ06dPtzERACBZOOv6\nAwCO069fP917771auHChYrGYLrroIv3kJz+xOxYAIAlQNAGoqKhIRUVFdscAACQZDp0DQILs27dP\nl112mWbMmKE77rhD0WjU7kjfyyuvvKILL7xQF154oVavXm13HADtGHs0ASABGhsbdcUVV+jTTz+V\nJG3atEkul0u33nqrzcn+NZs3b9avfvUrffHFF5Kk0tJS5ebmatiwYTYnA9AesUcTABJg3759OnDg\nQHy5ublZH3zwgY2Jvp+XXnopXjIl6fDhw+zVBPC9UTQBIAGysrLk9/tbrAsEAjal+f769Omj1NTU\n+LLH41FeXp6NiQC0ZxRNAEiArKwsXX311erevbtCoZDOPPNM3XXXXXbH+pf99Kc/1fjx49WpUydl\nZWVp3Lhxmj17tt2xALRTnKMJAAly1VVX6aKLLtJXX32l0047TV6v1+5I/zK3262FCxfq0KFDisVi\n6tatm1wul92xALRT7NEEgASJxWLasGGD1q5dq71799od53tzuVzq1q2bunfvTskEcErYowkACXL9\n9dfH7xu/ZMkSPfTQQzrnnHPsjgUAtmGPJgAkwIEDB/S3v/0tft/4Q4cO6ZFHHrE5FQDYi6IJAAnQ\n3Nx83AXaY7GYTWkAoG2gaAJAApx++un64Q9/KLf76/+sZmVlaebMmTanAgB7cY4mACSA2+3W008/\nrT/84Q/at2+fpk+frjFjxtgdCwBsRdEEgARJTU3VTTfdZHcMAGgzOHQOAAAAIyiaAJBgsVhMDz/8\nsGbOnKnLL79ce/bssTsSANiCQ+cAkGCPPPKIHnnkETU0NEiS9u/fr7Vr18rn89mcDACsxR5NAEiw\nd955J14yJWnPnj0qLS21MREA2IOiCQAJ5vf7WywHAgF16tTJpjQAYB+KJgAkyHvvvafJkydr27Zt\nCgaD8vv9ysnJ0aWXXqru3bvbHQ8ALMc5mgCQAHV1dbrxxhtVVlYWXzdp0iTddddd6tKli43JAMA+\n7NEEgAQ4cOCADh8+3GJdZWUlJROAo1E0ASABunbtqszMzBbrcnJybEoDAG0DRRMAEiAQCOjXv/61\nzjjjDPXo0UOjRo3Svffea3csALAV52gCQIJMmjRJkyZNUjQaldvN53gAcMVisZjdIVqroaFBDQ0N\nakeRT5nb7VY0GrU7hqVcLpdSU1PV1NTErJOYU+csWTfrTz75RI899ph8Pp/mzZtn2yWWnDprp/1N\n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\n/wPupitjAMddIwAAAABJRU5ErkJggg==\n",
706 | "text": [
707 | ""
708 | ]
709 | },
710 | {
711 | "metadata": {},
712 | "output_type": "pyout",
713 | "prompt_number": 31,
714 | "text": [
715 | ""
716 | ]
717 | }
718 | ],
719 | "prompt_number": 31
720 | },
721 | {
722 | "cell_type": "code",
723 | "collapsed": false,
724 | "input": [],
725 | "language": "python",
726 | "metadata": {},
727 | "outputs": []
728 | }
729 | ],
730 | "metadata": {}
731 | }
732 | ]
733 | }
--------------------------------------------------------------------------------
/notebooks/05 - What's next.ipynb:
--------------------------------------------------------------------------------
1 | {
2 | "metadata": {
3 | "name": ""
4 | },
5 | "nbformat": 3,
6 | "nbformat_minor": 0,
7 | "worksheets": [
8 | {
9 | "cells": [
10 | {
11 | "cell_type": "markdown",
12 | "metadata": {},
13 | "source": [
14 | "# The Future"
15 | ]
16 | },
17 | {
18 | "cell_type": "markdown",
19 | "metadata": {},
20 | "source": [
21 | "`ggplot` is still rough. We need to:\n",
22 | "\n",
23 | "- improved options for scales and geoms\n",
24 | "- improved legends\n",
25 | "- fix up facets"
26 | ]
27 | },
28 | {
29 | "cell_type": "code",
30 | "collapsed": false,
31 | "input": [
32 | "from ggplot import *\n",
33 | "%matplotlib inline"
34 | ],
35 | "language": "python",
36 | "metadata": {},
37 | "outputs": [
38 | {
39 | "output_type": "stream",
40 | "stream": "stderr",
41 | "text": [
42 | "/usr/local/lib/python2.7/site-packages/numpy/oldnumeric/__init__.py:11: ModuleDeprecationWarning: The oldnumeric module will be dropped in Numpy 1.9\n",
43 | " warnings.warn(_msg, ModuleDeprecationWarning)\n"
44 | ]
45 | }
46 | ],
47 | "prompt_number": 2
48 | },
49 | {
50 | "cell_type": "markdown",
51 | "metadata": {},
52 | "source": [
53 | "## [mpld3](https://github.com/jakevdp/mpld3)\n",
54 | "Output matplotlib figures as d3 charts."
55 | ]
56 | },
57 | {
58 | "cell_type": "code",
59 | "collapsed": false,
60 | "input": [
61 | "from mpld3 import enable_notebook, save_json\n",
62 | "enable_notebook()\n",
63 | "\n",
64 | "p = ggplot(aes(x='price'), data=diamonds)\n",
65 | "p + geom_histogram()"
66 | ],
67 | "language": "python",
68 | "metadata": {},
69 | "outputs": [
70 | {
71 | "output_type": "stream",
72 | "stream": "stderr",
73 | "text": [
74 | "stat_bin: binwidth defaulted to range/30.\n",
75 | " Use 'binwidth = x' to adjust this.\n"
76 | ]
77 | },
78 | {
79 | "html": [
80 | "\n",
81 | "\n",
82 | "\n",
85 | "\n",
86 | "\n",
87 | ""
123 | ],
124 | "metadata": {},
125 | "output_type": "display_data",
126 | "png": "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\ng3IKAAAAY1BOAQAAYAzKKQAAAIxBOQUAAIAxKKcAAAAwBuUUAAAAxqCcAgAAwBiUUwAAABiDcgoA\nAABjUE4BAABgDMopAAAAjEE5BQAAgDEopwAAADAG5RQAAADGoJwCAADAGJRTAAAAGINyCgAAAGNQ\nTgEAAGAMyikAAACMQTkFAACAMSinAAAAMAblFAAAAMagnAIAAMAYlFMAAAAYw7Pcg93d3RodHVVV\nVZUOHTokSUomk+rq6tLNmzdVXV2t9vZ2+f1+SVJfX58GBgZkWZZaWlq0efNmSVIsFlN3d7fS6bQi\nkYhaWlokSel0WidPntS1a9fk9/vV3t6u6urqQp4vAAAADLbsldMnn3xSHR0dS7b19/dr06ZN6uzs\n1KZNm9Tf3y9Jun79uoaGhnT48GF1dHTo9OnTymQykqRTp06pra1NnZ2dunHjhkZHRyVJ586dk9/v\nV2dnp5qamvT2228X4hwBAABQJpYtpxs2bFBFRcWSbSMjI9q1a5ckaefOnRoeHs5u3759u9xut8Lh\nsGpqajQ2NibbtjU/P6+GhoZ77rM41tatW3Xx4sX8nh0AAADKyrLL+veSSCQUCAQkSYFAQIlEQpJk\n23a2gEpSKBSSbdtyu90KhUJ3bV/cZ/Ext9stn8+nZDKpyspKxeNxTU9PLzl2IBCQx3P/KadSKaen\ntSyv15vX8YrJ7XaX9fyLbTFfK8kZbiNjzpCx3JAzZ8iZc2TMmUJma1UjW5aVr3nc5ezZs+rt7V2y\nbd++fdq/f/99943FYnmdS21tbV7Hg/nC4XCpp4AHHBlDMZAzlCPH5bSqqkq2bSsYDMq2bVVVVUmS\ngsGgpqamss+Lx+MKhUIKBoOKx+N3bb9zn1AopIWFBc3NzamyslKS1NjYqGg0uuTYgUBAk5OTSqfT\nzs90FcbHx4t6vHzy+Xyam5sr9TTKhsfjUTgcLknOyhUZc4aM5YacOUPOnCNjzixmrCBjO90hGo1q\ncHBQzc3NOn/+vLZs2ZLdfvz4cTU1Ncm2bU1MTKi+vl6WZcnn82lsbEz19fUaHBzUnj17loy1fv16\nXbhwQRs3bsweJxQKLfk4wKLx8fG8L9vfT7GPl08ej6es518q6XSa122FyFhuyJgz5Cw35GzlyJg5\nli2nXV1dunTpkpLJpF588UXt379fzc3NOnbsmM6dO5e9lZQk1dXVadu2bTpy5IhcLpdaW1uzy/6t\n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\n",
127 | "text": [
128 | ""
129 | ]
130 | },
131 | {
132 | "metadata": {},
133 | "output_type": "pyout",
134 | "prompt_number": 3,
135 | "text": [
136 | ""
137 | ]
138 | }
139 | ],
140 | "prompt_number": 3
141 | },
142 | {
143 | "cell_type": "code",
144 | "collapsed": false,
145 | "input": [],
146 | "language": "python",
147 | "metadata": {},
148 | "outputs": []
149 | }
150 | ],
151 | "metadata": {}
152 | }
153 | ]
154 | }
--------------------------------------------------------------------------------
/notebooks/06 - Under the Hood.ipynb:
--------------------------------------------------------------------------------
1 | {
2 | "metadata": {
3 | "name": ""
4 | },
5 | "nbformat": 3,
6 | "nbformat_minor": 0,
7 | "worksheets": [
8 | {
9 | "cells": [
10 | {
11 | "cell_type": "markdown",
12 | "metadata": {},
13 | "source": [
14 | "## I didn't get this far"
15 | ]
16 | },
17 | {
18 | "cell_type": "code",
19 | "collapsed": false,
20 | "input": [],
21 | "language": "python",
22 | "metadata": {},
23 | "outputs": []
24 | }
25 | ],
26 | "metadata": {}
27 | }
28 | ]
29 | }
--------------------------------------------------------------------------------