Created
September 7, 2013 08:31
-
-
Save coderforlife/6473909 to your computer and use it in GitHub Desktop.
Introduction to Scientific Python by using the IPython Notebook
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| { | |
| "metadata": { | |
| "name": "Python Tutorial" | |
| }, | |
| "nbformat": 3, | |
| "nbformat_minor": 0, | |
| "worksheets": [ | |
| { | |
| "cells": [ | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Welcome to <img alt='IPython Notebook' src='/static/ipynblogo.png' height=25>!\n", | |
| "======================================================\n", | |
| "\n", | |
| "This is a brief introduction to Python and the IPython Notebook. We will be around to help you with any questions you may have. If you are familiar with programming you will still want to skim this document for how to use IPython Notebook and how Python is different than what you already know.\n", | |
| "\n", | |
| "First we will start with some IPython Notebook features. IPython stands for Interactive Python. The notebook part of it is a web-based interactive computational environment where you can combine code execution, text, mathematics, plots and rich media into a single document.\n", | |
| "\n", | |
| "The notebook is split into different \"Cells\". Each cell contains one kind of content, such as code, text, formulas for display, ... This allows you to write your thoughts inbetween sections of code. This text here is a cell; double-clicking it will allow you to edit it.\n", | |
| "\n", | |
| "Code cells can be run on there own, but will remember all the results from the previously run cell. As you go through this tutorial you should try to modify the contents of the cell to explore the features of Python - making sure you understand every line. You can run the same cell over and over again, or you can add new cells using the menu above.\n", | |
| "\n", | |
| "When you want to take your work \"home\", you can use the \"File\" menu to download as a notebook or a standard Python file.\n", | |
| "\n", | |
| "*Note*: Python is similar to MATLAB. If you are used to MATLAB I recommend checking out http://www.scipy.org/NumPy_for_Matlab_Users which will tell you all of the important differences. Biggest thing to remember is that arrays / matrices are 0-based, not 1-based.\n", | |
| "\n", | |
| "*Note 2*: This notebook is setup with the following code by default, so if you try to do this in elsewhere you will need to add these lines:\n", | |
| "\n", | |
| " from numpy import * # numeric Python tools\n", | |
| " from scipy import * # scientific Python tools\n", | |
| " from pylab import * # plotting Python tools\n", | |
| " from __future__ import division # makes the division operator work as you would expect\n" | |
| ] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Basics\n", | |
| "------\n", | |
| "First, any text after a `#` symbol is a comment and is ignored by Python. You should be in the practice of commenting your code thoroughly so that someone else will know what it is doing and so you will know in a couple months when you go back and look at it (you think you'll remember but you won't).\n", | |
| "\n", | |
| "In Notebook you could add it as a text cell, but you will still want comments to be within your code.\n", | |
| "\n", | |
| "In the Notebook there are shortcut keys for executing cells:\n", | |
| "\n", | |
| "* `Shift + Enter` to run the current cell and move to the next one\n", | |
| "* `Ctrl + Enter` to run the current cell in-place\n", | |
| "\n", | |
| "Simple math is pretty straight forward:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "# Note: print makes you output the result\n", | |
| "# In IPython Notebooks, the last thing you do will automatically print out if it did not have = in it (we will learn about = in a bit)\n", | |
| "print 2 + 2 # prints 4\n", | |
| "print (50-5*6)/4 # prints 5\n", | |
| "print 3**3 # prints 27 (3^3)\n", | |
| "print 7 / 2 # prints 3.5\n", | |
| "print abs(-5) # prints 5\n", | |
| "print round(5.53) # prints 6\n", | |
| "round(5.53, 1) # prints 5.5" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "At any time if you want to know what a function does you can add `?` after the function name and run the cell.\n", | |
| "\n", | |
| "Note: in normal Python you would have to do `help(round)`" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "round?" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "You will also notice that while typing in a code cell you pause after `round(` it will give you the help information. Try it by adding a new cell block below!" | |
| ] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Also, IPython Notebook will 'autocomplete' things for you when you press tab. Typing `rou` and pressing tab will give you a list of options. This can save you from typing long names! Try it in a new cell block below." | |
| ] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "You can create variables to hold values:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "x = 2 + 2 # assigns 4 to the variable x\n", | |
| "y = x * 3 # assigns 12 to the variable y\n", | |
| "y / 2 # prints 6" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "In IPython Notebook, when you run a cell that defines variables they will stick around for all subsequent cells you run. You could add a cell here and get the values of `x` and `y`." | |
| ] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Strings\n", | |
| "-------\n", | |
| "\n", | |
| "A string is a piece of text enclosed in either single or doule quotes" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "print \"Hello World\"\n", | |
| "'It is a beautiful day'" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "You can concatenate strings to each other:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "\"How \" + \"are you?\"" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "You can convert numbers to a str:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "str(2+2) # Try: str(x) using the value of x from the first section" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "You can even concatenate numbers to a string by first converting:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "\"2 + 2 equals: \"+str(2+2) # Try: str(x) using the value of x from the first section" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "There are an incredible number of built-in functions for working with strings. For more information see http://docs.python.org/library/stdtypes.html#string-methods\n", | |
| "\n", | |
| "Strings also provide a very rich formatting syntax, however it is a bit much for this guide. For more information see http://docs.python.org/library/string.html#format-specification-mini-language" | |
| ] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Lists\n", | |
| "-----\n", | |
| "Lists are many variables rolled into one that have a specific order. Lists in Python are quite powerful and versatile.\n" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "num_list = [5, 0, 2, 6] # a list of a few numbers\n", | |
| "str_list = ['Hello','World', # a list of strings, can be across many lines\n", | |
| " 'How','Are','You?'] # however the other lines must be indented\n", | |
| "\n", | |
| "print len(num_list) # prints 4, the number of items in the list\n", | |
| "print min(num_list) # prints 0, the minimum in the list\n", | |
| "print max(str_list) # prints You?, the maximum of the list\n", | |
| "# Note: Strings also support len, min, max" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Lists support `+` and `*` for concatenation and repetition respectively" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "num_list+str_list" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "num_list*2" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Python lists are zero-based (unlike Matlab which is one-based). This means that the first item in a list has the index `0`. You can retrieve and modify items by index:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "x = num_list[1] # x is 0, the second element of num_list\n", | |
| "x # Put this here by itself so we Notebook will show us the value" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "num_list[2] = 99\n", | |
| "num_list" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "To add and remove elements from a list use `append` and `del`:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "num_list.append(200) # num_list is now [5, 0 99, 6, 200]\n", | |
| "del num_list[1] # num_list is now [5, 99, 6, 200]\n", | |
| "num_list" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Python lists support 'slices' which are portions of a list" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "num_list[1:3] # The second through third values in the list\n", | |
| "# Note: the range includes the first number and goes up to the second number but does not include it" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Each side of the slice is optional and if not included means go to the end:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "print num_list[1:] # from the second element to the end\n", | |
| "print num_list[:3] # from the start to the third element\n", | |
| "print num_list[:] # the entire list" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Negative slice values mean from the end" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "print num_list[:-1] # from the start to the second to last element\n", | |
| "print num_list[1:-1] # from the second to the second to last element\n", | |
| "print num_list[-1:] # from the second to last element to the end" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| " And even more advanced with a third value for an increment:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "num_list[::2] # every other element" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Slices can be be replaced and deleted:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "str_list[1:2] = num_list # str_list is now ['Hello',5,99,6,200,'How','Are','You?']\n", | |
| "del str_list[1:5] # str_list is now ['Hello','How','Are','You?']\n", | |
| "str_list" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Lists support many useful functions including `sort()` and `reverse()`. See http://docs.python.org/library/stdtypes.html#mutable-sequence-types for more information.\n", | |
| "\n", | |
| "Another powerful feature of Python lists is list comprehensions, but they are a bit complicated. If you want to learn more, see: http://docs.python.org/tutorial/datastructures.html#list-comprehensions" | |
| ] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Tuples\n", | |
| "------\n", | |
| "\n", | |
| "Tuples are similar to lists but a little less powerful. Instead of using `[]` tuples use `()` when being created. Tuples are fixed in length and cannot be changed. They are most useful for things like coordinates (e.g `(x, y)`), having functions return more than one value, and read-only lists. Below are some examples. Lists and tuples can be coverted to each other: `tuple(aList)` and `list(aTuple)`" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "coord = (4, 5) # packs a tuple\n", | |
| "coord = 4, 5 # same as above\n", | |
| "x, y = coord # unpacks a tuple\n", | |
| "x = coord[0] # they support many of the list features\n", | |
| "coords = [ (1, 2), (3, 4), (4, 5) ] # a list of tuples\n", | |
| "x, y = coords[2] # x is 4, y is 5" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Booleans\n", | |
| "--------\n", | |
| "\n", | |
| "Booleans are values that are either `True` or `False`. They are typically used in conditional tests (which we will get to in the very soon section). When using a value as a boolean, any of the following are considered `False`:\n", | |
| "\n", | |
| " False, 0, \"\", [], (), None\n", | |
| "\n", | |
| "Everything else is `True`.\n", | |
| "\n", | |
| "Try: adding print statements or extra cells to see the outputs below, currently nothing below is output." | |
| ] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "The basic boolean operations are `not`, `and`, and `or`:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "t = True\n", | |
| "f = not t # False (not switches True to False and False to True)\n", | |
| "b = t and t # True (and is True only if both are True)\n", | |
| "b = t and f # False (and is False if either is False)\n", | |
| "b = f and f # False\n", | |
| "b = t or t # True (or is True if either is True)\n", | |
| "b = t or f # True\n", | |
| "b = f or f # False" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "You can also make booleans by comparisons:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "x = 5\n", | |
| "b = x > 4 # True (greater than)\n", | |
| "b = x >= 4 # True (greater than or equal to)\n", | |
| "b = x < 4 # False (less than)\n", | |
| "b = x <= 4 # False (less than or equal to)\n", | |
| "b = x == 4 # False (equals)\n", | |
| "b = x != 4 # True (not equals), can also be written 5 <> 4\n", | |
| "b = 4 < x < 6 # True, same as 4 < x and x < 6" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Comparisons work for strings as well, but be careful since by default uppercase letters come before lowercase letters" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "b = \"aardvark\" < \"zebra\" # True\n", | |
| "b = \"aardvark\" < \"Zebra\" # False\n", | |
| "b = \"Yes\" == 'Yes' # True" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "There are special comparisons for lists (also work for strings and tuples):" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "l = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]\n", | |
| "b = x in l # True (the list contains 5)\n", | |
| "b = x not in l # False" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Conditionals (`if` statements)\n", | |
| "------------------------------\n", | |
| "\n", | |
| "We are finally getting to the interesting stuff. If statements let you run a chunk of run code if and only if something is True. First lets set some variables to known values:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "x, y = 5, 10" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Then, lets check if x is positive:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "if x > 0:\n", | |
| " print \"x is positive\"" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "This will only print \"x is positive\" if x is positive. Try changing the value of x.\n", | |
| "\n", | |
| "Your value of x could come from many places, maybe a file, maybe from the user, maybe from some really complicated calculations.\n", | |
| "\n", | |
| "You can also compare two variables to each other:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "if x > y:\n", | |
| " print \"x is greater than y\"\n", | |
| "else:\n", | |
| " print \"x is less than or equal to y\"" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "We added an `else` there which runs in case the `if` statement was `False`.\n", | |
| "\n", | |
| "You can chain multiple `if`s together using `elif` which stands for 'else if'" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "if x > 0:\n", | |
| " print \"x is positive\"\n", | |
| "elif x < 0:\n", | |
| " print \"x is negative\"\n", | |
| "else: # at this point x cannot be positive or negative\n", | |
| " print \"x is 0\"" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Indentation is very important in Python. Here is an example to help explain indentation importance:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "if x > 0:\n", | |
| " print \"x is positive\"\n", | |
| "elif x < 0:\n", | |
| " # this group has two lines, both have the same indentation\n", | |
| " x = -x\n", | |
| " print \"x was negative, but now is positive\"\n", | |
| " # this group is done so the next line is un-indented\n", | |
| "else:\n", | |
| " print \"x is 0\"" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Another more complicated example:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "if x > 0:\n", | |
| " print \"x is positive\"\n", | |
| " if x > y:\n", | |
| " # if statements can be inside if statements, you just need to indent again\n", | |
| " print \"x is above y\"\n", | |
| " else: # this else is paired with \"if (x > y):\" because of its indentation\n", | |
| " print \"x is at most y\"\n", | |
| " print \"wasn't that interesting?\"\n", | |
| "else: # this else is paired with \"if (x > 0):\" because of its indentation\n", | |
| " print \"x is not positive\"" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "`while` Loops\n", | |
| "-------------\n", | |
| "\n", | |
| "So now that we have conditional statements down, lets add on loops. The simplest loop is a while loop. Below is an example. Do you recongnize the pattern of numbers? The while loop will repeatedly run the code inside it until it's conditional statement is False. So you can compute more of this series by changing\n", | |
| "\n", | |
| " while b < 20:\n", | |
| "\n", | |
| "to\n", | |
| "\n", | |
| " while b < 2000:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "a, b = 0, 1\n", | |
| "while b < 20:\n", | |
| " print b # Try: putting a , after the b here, it prevents the newline from being adding\n", | |
| " a, b = b, a+b" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "`for` Loops\n", | |
| "-----------\n", | |
| "\n", | |
| "The truth is that you probably won't use while loops too much because their big brother the \"for loop\" is much more convient." | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "a = ['cat', 'window', 'defenestrate']\n", | |
| "for x in a: # for loops can take any 'iterable' object\n", | |
| " print x, len(x)\n", | |
| "\n", | |
| "for letter in a[0]:\n", | |
| " print letter" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "If you need to cover a range of values, then you use the conveniently named `range()` function:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "for i in range(len(a)): # Goes from i = 0 to len(a)-1 (so 0, 1, 2 in this case)\n", | |
| " print i, a[i]\n", | |
| "\n", | |
| "# This particular example can also be done with 'enumerate'\n", | |
| "for i, string in enumerate(a):\n", | |
| " print i, string" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "`range()` creates a list of numbers based on what you give it. You can also make it not start at zero, skip numbers, and go downwards:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "print range(5)\n", | |
| "print range(5, 10)\n", | |
| "print range(0, 10, 3)\n", | |
| "print range(-10, -100, -30)" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Basically `range(start, end, step)` with `start` and `step` being optional" | |
| ] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Functions\n", | |
| "---------\n", | |
| "\n", | |
| "If you find yourself writing the same lines of code over and over, or if you just need to organize your code (always a good thing), you can create functions. Functions are mini-programs that take a set of inputs and give an optional set of outputs. Here is a basic example:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "def minimum(a, b): # define a function called 'minimum' that takes two inputs: 'a' and 'b'\n", | |
| " if a < b:\n", | |
| " return a # the return keyword gives the outputs\n", | |
| " else:\n", | |
| " return b" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "The above function finds the minimum of two values. You can use it like so:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "minimum(5, 10)" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Note: like variables, once you run a cell that defines a function it is available for all other cells you run\n", | |
| "\n", | |
| "Since the return function immediately stops the function, the `minimum` function could be simplified to:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "def minimum(a, b):\n", | |
| " if a < b:\n", | |
| " return a\n", | |
| " return b" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "You can also return more than one value. The function below returns both the minumum and maximum value." | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "def min_max(a, b):\n", | |
| " if a < b:\n", | |
| " return a, b\n", | |
| " return b, a" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "min_max(10, 5)" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Note: this was just a simple example and for minimum and maximum you would use the built-in `min()` and `max()` functions." | |
| ] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "***********************************\n", | |
| "Exercise: Fibonacci Series Function\n", | |
| "-----------------------------------\n", | |
| "\n", | |
| "To see that you understand the basics, write a function that computes the Fibonacci series up to a given value. It should store every value in a list and return that list (not print anything).\n", | |
| "\n", | |
| "Tip: the example `while` loops printed the Fibonacci series, so you have the algorithm." | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "def fib(max_value):\n", | |
| " l = []\n", | |
| " # TODO: fill in the list 'l' with the Fibonacci values up to and including max_value then return the list" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "fib(20) # should output [1, 1, 2, 3, 5, 8, 13]" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "fib(2000) # should output [1, 1, 2, 3, 5, 8, 13, 21, 34, 55, 89, 144, 233, 377, 610, 987, 1597]" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "*****" | |
| ] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Dictionaries\n", | |
| "------------\n", | |
| "\n", | |
| "We previously learned about lists and tuples. There is another very powerful built-in data structure called a dictionary (or `dict`). It associates a set of keys with values. You use the `{}` to define it. For example:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "charges = { \"K\" : 1, \"Na\" : 1, \"H\" : 1, \"Ca\" : 2, \"Mg\" : 2, \"Cl\" : -1 }" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "charges[\"Ca\"] # lookup the charge of Calcium" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "\"K\" in charges # do we have an entry for potassium?" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "You can even loop over all the keys:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "for ion in charges:\n", | |
| " print ion + \" has a charge of \" + str(charges[ion])" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "The keys do not have to be strings but can also be tuples, numbers, and many other things:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "xy = { (1,1) : -5, (2,4) : 45, (-4,6) : 0 }" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "The values can be anything (numbers, strings, lists, dictionaries, ...)." | |
| ] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Errors\n", | |
| "------\n", | |
| "\n", | |
| "It is invetible that you will run into errors in your code so you need to understand the common errors, what they mean, and how to work on fixing them.\n", | |
| "\n", | |
| "Probably the most common error is a `SyntaxError`. This basically means that you tried to run a program that doesn't follow the rules of the Python language. Try executing the cell below and you will get a syntax error (the list must end with `]`)." | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "x = [5, 6, 7)" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "The little `^` indicates where the problem is. The file is a random name because we are in a Notebook.\n", | |
| "\n", | |
| "Sometimes a syntax error on a previous line causes Python to complain on a future line so make sure to check the line before if you can't find a problem with the given line.\n", | |
| "\n", | |
| "A special type of the `SyntaxError` is the `IndentationError` meaning Python expected an indentation and you didn't indent, for an example run the following cell:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "if x > 5:\n", | |
| "print 'This line should be indented'" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Other errors give a \"traceback\" where it tells you all the functions being called with the second to last being the line that caused the error at the and the last line being a description of the problem. For example, the following cell will do a division by zero (which is undefined)." | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "def divZero(x):\n", | |
| " return x / 0\n", | |
| "divZero(5)" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "**Other Common Errors**\n", | |
| "\n", | |
| "`NameError: name 'spam' is not defined` - You tried to use a variable named \"spam\" but it does not exist yet.\n", | |
| "\n", | |
| "`IndexError: list index out of range` - You tried to access an element in a list or array that is >=len(list), for example:\n", | |
| " \n", | |
| " x = [1, 2, 3]\n", | |
| " x[5] # generates error\n", | |
| "\n", | |
| "`TypeError: cannot concatenate 'str' and 'int' objects` - You tried to \"add\" a string and a number like so: `\"hello\" + 5`, to do this properly you must do `\"hello\" + str(5)`\n", | |
| "\n", | |
| "`TypeError: divZero() takes exactly 1 argument (0 given)` - You called a function with the wrong number of inputs. This is the error you would get if you ran `divZero()`.\n", | |
| "\n", | |
| "`ImportError: No module named foo` - You tried to import the module named foo but it doesn't exist. Either you typed the name wrong or you haven't properly installed the module.\n", | |
| "\n", | |
| "`IOError: [Errno 2] No such file or directory: 'x.txt'` - All `IOErrors` deal with problems with files. In this case we tried to open the file 'x.txt' which doesn't exist.\n", | |
| "\n", | |
| "`AttributeError: 'list' object has no attribute 'bar'` - You tried to access an property or function of an object that doesn't exist. For example:\n", | |
| "\n", | |
| " x = [1, 2, 3]\n", | |
| " x.foo() # Since lists have no foo function, this causes an error.\n", | |
| "\n", | |
| "`ValueError: list.remove(x): x not in list` - A `ValueError` means that a function received an unexpected value. For example:\n", | |
| "\n", | |
| " x = [1, 2, 3]\n", | |
| " x.remove(6) # Since there is no \"6\" in the list it causes an error.\n", | |
| "\n", | |
| "There are many other errors, but these are the most common ones. Hopefully you won't see them too often, and never see the less common ones." | |
| ] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Advanced\n", | |
| "--------\n", | |
| "\n", | |
| "There are tons of other advanced things that are built into Python. Ask us and we may be able to help you use them. Here is a brief list of things you may use:\n", | |
| "\n", | |
| " * classes / namespaces\n", | |
| " * complex numbers\n", | |
| " * lambda functions\n", | |
| " * sets, queues, and stacks\n", | |
| " * list comprehensions\n" | |
| ] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "**************************\n", | |
| "NumPy / SciPy / matplotlib\n", | |
| "==========================\n", | |
| "\n", | |
| "Now we get to the really interesting stuff. NumPy and SciPy provide advanced math and scientific functions for Python. They provide nearly all of the functionality of MATLAB for Python (see http://www.scipy.org/NumPy_for_Matlab_Users for differences). In fact, internally they use many of the same libraries!\n", | |
| "\n", | |
| "The NumPy and SciPy modules (a.k.a. libraries) needs to imported to be used and you would usually do something like `from scipy import *` but IPython Notebook does that for us.\n", | |
| "\n", | |
| "Note: NumPy is actually a subset of SciPy, so everything in NumPy is also in SciPy\n", | |
| "\n", | |
| "NumPy and SciPy are fully documented online at http://docs.scipy.org/doc/numpy/reference/ and http://docs.scipy.org/doc/scipy/reference/ respectively along with inside the code (using `fft?` or `fft(` and waiting a second). The help includes examples. Try it out!\n", | |
| "\n", | |
| "matplotlib is the plotting module for Python and we will get to it in a few sections." | |
| ] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Arrays\n", | |
| "------\n", | |
| "\n", | |
| "So you know how we learned about lists? Well it turns out that for the most part you want to use a SciPy array and not a list. They are much faster for many things and when used with SciPy the benefits are amazing. The good news is that they act almost the same as the normal Python lists.\n", | |
| "\n", | |
| "Some simple 1-dimensional array examples:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "a1 = array([1, 2, 3, 4])\n", | |
| "a2 = array([4, 3, 2, 1])\n", | |
| "a3 = a1 + a2 # add array element-wise (normal Python lists would concatenate)\n", | |
| "print a3 # prints [5, 5, 5, 5]\n", | |
| "print a1[0] # prints [1]\n", | |
| "print a2[1:3] # prints [3, 2] (all the other slice operations work as well)\n", | |
| "a4 = a1 * a2 # multiply arrays element-wise\n", | |
| "a5 = sin(a1); # takes sin of all elements\n", | |
| "a6 = log(a2); # takes natrual log of all elements\n", | |
| "a7 = exp(a6); # computes e^(x) for each x in the array\n", | |
| "a8 = 10**a1; # computes 10^(x) for each x in the array\n", | |
| "py_list = a4.tolist() # converts to a Python list\n", | |
| "a4_dup = array(py_list) # converts to a NumPy array" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "There are many more available functions, commonly used ones are:\n", | |
| "\n", | |
| "`sum`, `mean`, `std`, `cumsum`, `append`, `concatenate`, `amin`, `amax`, `argmin`, `argmax`, `histogram`, `round`, `sign`, `unique`\n", | |
| "\n", | |
| "For a complete list with examples see: http://www.scipy.org/Numpy_Example_List_With_Doc" | |
| ] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "More ways to make a 1-D array:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "r = arange(0, 50, 1) # like Python range but with real-valued SciPy arrays\n", | |
| "l = linspace(0, 50, 10000) # 10000 element array from 0 to 50 (inclusive)\n", | |
| "z = zeros(50) # an array of 50 zeros\n", | |
| "o = ones(50) # an array of 50 ones\n", | |
| "p = pi*ones(50) # an array of 50 pis" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Matrices\n", | |
| "--------\n", | |
| "\n", | |
| "SciPy arrays can also be multi-dimensional (matrices are 2-dimensional arrays)." | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "m1 = array([[1, 2, 3, 4], # 3 rows and 4 columns\n", | |
| " [4, 3, 2, 1],\n", | |
| " a3 ])\n", | |
| "m2 = zeros((4, 5)) # 4 rows and 5 columns of zeros - note the double parathesis, these are critical" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Get the shape:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "print m2.shape # prints (4, 5)\n", | |
| "nrows, ncols = m2.shape\n", | |
| "nrows # outputs 4, the number of rows" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "To access elements in a matrix:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "m2[3,0] = 5 # Changes fourth row and first column to 5, same as m2[3][0]\n", | |
| "print m1[1,:] # Prints the entire second row (same as m2[1])\n", | |
| "print m1[:,2] # Prints the entire third column\n", | |
| "# The other slice operations work as well:\n", | |
| "m1[1:3,1:3] # Outputs: [[3 2] # second row, second and third columns\n", | |
| " # [5 5]] # third row, second and third columns" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Matrices support +, *, ** (power), sin, log, ... the same way that arrays do (element-wise operations, no need for `.*` or `./` like in MATLAB).\n", | |
| "\n", | |
| "They also support some matrix-only operations:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "t = transpose(m2) # switch rows and columns in the array / matrix\n", | |
| "t = m2.T # same as above\n", | |
| "m = m1.dot(m2) # dot product (like * in MATLAB)" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Some common matrix functions to look into are `reshape` and `histogram2d`.\n", | |
| "\n", | |
| "Note: SciPy/NumPy actually has something called `matrix` as well, which acts like MATLAB matrices where `*` is the matrix multiplication (it is designed for linear algebra)." | |
| ] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Finding\n", | |
| "-------\n", | |
| "\n", | |
| "SciPy arrays and matrices can easily be searched. You can use the comparison operators we learned before to get an `array` / `matrix` of `True` / `False` values for each element like so:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "a = array([-1, 0, 5, -5, 7])\n", | |
| "b = array([-2, 4, -1, 0, 8])\n", | |
| "print a > 0 # prints [False False True False True]\n", | |
| "print b > a # prints [False True False True True]" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Check is any / all are `True`:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "print \"Are any negative? \"+str(any(a < 0))\n", | |
| "print \"Are all negative? \"+str(all(a < 0))" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "If you need the indices, you can use the `nonzero()` function (since `False` is equal to `0`, it skips all `False`s):" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "nonzero(a >= 0)" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "To get the values you can use the `nonzero()` result as an index:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "a[nonzero(a >= 0)]" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Using these techniques we can find spike times in voltage data (at the moment we don't have any data, so this won't work, so just make a note of it):" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "threshold = 0 # the spike threshold\n", | |
| "time = # when we sampled voltage\n", | |
| "voltage = # what the voltage was\n", | |
| "spikes = time[nonzero(logical_and(voltage[:-1] < threshold, voltage[1:] >= threshold))] # find all time points when previous voltage was below threshold and next votlage was above threshold" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Files\n", | |
| "-----\n", | |
| "\n", | |
| "You will need to be able to get your data into Python to make use of it. Arrays and matrices can easily be read from and saved to files." | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "# Save array / matrix:\n", | |
| "save('test.npy', m2) # binary format (smallest)\n", | |
| "savetxt('test.txt', m2) # text format (easiest to read as text)\n", | |
| "savetxt('test.csv', m2, delimiter=',') # comma-seperated values format (easily usable by Excel)" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "# Load array / matrix\n", | |
| "m3 = load('test.npy')\n", | |
| "m3 = genfromtxt('test.txt')\n", | |
| "m3 = genfromtxt('test.csv', delimiter=',')" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "You can also save many arrays / matrices into a single compressed file using `savez`. Those files should have the extension 'npz'.\n", | |
| "\n", | |
| "Can also use `io.loadmat` and `io.savemat` to read and write MAT files from MATLAB." | |
| ] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Plotting\n", | |
| "--------\n", | |
| "\n", | |
| "You can also make beautiful plots with Python. Within IPython Notebook they show up right in the notebook!" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "# First we create data for a sin wave, jsut to have something to show\n", | |
| "x = linspace(-2*pi, 2*pi, 5000) # create a list of numbers\n", | |
| "y = sin(x) # calculate the sin for each point\n", | |
| "\n", | |
| "# Now plot it\n", | |
| "figure() # creates a new figure to plot in\n", | |
| "title('sin curve') # add a title\n", | |
| "xlabel('X values') # add an x label\n", | |
| "ylabel('Y values') # add a y label\n", | |
| "plot(x, y) # plot x vs y\n", | |
| "# In regular Python you would need a show() command to show the plot." | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "There are an incredible number of options for plotting your data just the way you want, and you can have multiple plots at the same time." | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "y2 = cos(x) # calculate the cos for each point\n", | |
| "figure()\n", | |
| "title('sine and cosine curves')\n", | |
| "xlabel('X values')\n", | |
| "ylabel('Y values')\n", | |
| "plot(x, y, color='red', linestyle='-.', label='sin(x)') # shorthand is plot(x, y, 'r-.', label='sin(x)')\n", | |
| "plot(x, y2, color='green', linestyle='--', label='cos(x)') # shorthand is plot(x, y2, 'g--', label='cos(x)')\n", | |
| "legend(loc='upper right') # uses the 'label' for each" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "For a complete list of options see http://matplotlib.sourceforge.net/api/pyplot_api.html#matplotlib.pyplot.plot\n", | |
| "\n", | |
| "You can also do 2D plots:" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "# Generate some 'interesting' data (just ignore this part)\n", | |
| "from matplotlib.mlab import bivariate_normal\n", | |
| "x, y = arange(-3.0, 3.0, 0.025), arange(-2.0, 2.0, 0.025)\n", | |
| "X, Y = meshgrid(x, y)\n", | |
| "Z1 = bivariate_normal(X, Y, 1.0, 1.0, 0.0, 0.0)\n", | |
| "Z2 = bivariate_normal(X, Y, 1.5, 0.5, 1.0, 1.0)\n", | |
| "Z = 10.0 * (Z2 - Z1)\n", | |
| "\n", | |
| "# Contour plot\n", | |
| "figure()\n", | |
| "title('Contour Plot')\n", | |
| "contour(X, Y, Z)\n", | |
| "colorbar() # adds a color bar to the image\n", | |
| "\n", | |
| "\n", | |
| "# Image plot\n", | |
| "figure()\n", | |
| "title('Image Plot')\n", | |
| "imshow(Z, extent=[amin(X), amax(X), amin(Y), amax(Y)], aspect='auto', origin='lower')\n", | |
| "colorbar()\n" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Other plot types that may be useful:\n", | |
| "\n", | |
| " * line plot: `errorbar`, `fill`, `fill_betweenx`\n", | |
| " * box plots: `bar`, `barh`, `hist`, `boxplot`\n", | |
| " * vector field: `quiver`, `barbs`\n", | |
| " * 2D plots: `contourf`\n", | |
| " * spectral: `specgram`, `psd`, `csd`\n", | |
| " * other: `polar`, `scatter`, `acorr`, `xcorr`\n", | |
| "\n", | |
| "Other functions to perfect the figure:\n", | |
| "\n", | |
| " * `annotate`, `subtitle`, `clim` (color scale limits)\n", | |
| " * `axis`, `twinx`/`twiny` (create second axis), `xscale`/`yscale` (set log scale)\n", | |
| "\n", | |
| "See the matplotlib homepage for complete documentation and tons of examples: http://matplotlib.sourceforge.net/" | |
| ] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "************************\n", | |
| "Exercise: Spike Analysis\n", | |
| "------------------------\n", | |
| "\n", | |
| "We have a voltage trace from a neuron over 1 second and we want to do some simple analysis on it." | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "data = loadtxt('trace.txt') # load the data\n", | |
| "time = data[:, 0] # milliseconds (ms)\n", | |
| "voltage = data[:, 1] # millivolts (mV)" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "First, plot the trace. Make sure to include proper labels. What is the minimum and maximum voltage of the cell during this recording? (Note: use `amin` and `amax` to get the min and max of an array)" | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "figure()\n", | |
| "xlabel('Time (ms)')\n", | |
| "ylabel('Voltage (mV)')\n", | |
| "plot(time, voltage)\n", | |
| "print amin(voltage), amax(voltage)" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Calculate the times at which spikes occur (hint: there is code to do this earlier in the tutorial). Show a raster plot." | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "spike_times = time[nonzero(logical_and(voltage[:-1] < 0, voltage[1:] >= 0))] # find all time points when previous voltage was below threshold (0) and next votlage was above threshold (0)\n", | |
| "\n", | |
| "figure(figsize = (10.0, 1.0)) # different size is better for the raster plot\n", | |
| "setp(gca().get_yticklabels(), visible=False) # hide y axis (a raster plot of a single cell does not need it)\n", | |
| "xlabel('Time (ms)')\n", | |
| "plot(spike_times, ones(spike_times.shape), 'b.')\n" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "Calculate the ISIs (inter-spike intervals). This is achieved by taking each spike time and subtracting the previous spike time. You can use the `[:-1]` and `[1:]` trick used for the calculation of spike times.\n", | |
| "\n", | |
| "Once you get the ISIs (in ms) convert it to spike frequency (Hz which is sec<sup>-1</sup>) and plot them vs the spike number. Calculate the min (`amin`), max (`amax`), mean (`mean`) and standard deviation (`std`) of the spike frequency." | |
| ] | |
| }, | |
| { | |
| "cell_type": "code", | |
| "collapsed": false, | |
| "input": [ | |
| "isis = spike_times[1:] - spike_times[:-1]\n", | |
| "freq = 1000 / isis\n", | |
| "\n", | |
| "figure()\n", | |
| "xlabel('Spike Number')\n", | |
| "ylabel('Spike Frequency (Hz)')\n", | |
| "plot(freq)\n", | |
| "\n", | |
| "print amin(freq), amax(freq), mean(freq), std(freq)" | |
| ], | |
| "language": "python", | |
| "metadata": {}, | |
| "outputs": [] | |
| }, | |
| { | |
| "cell_type": "markdown", | |
| "metadata": {}, | |
| "source": [ | |
| "*****" | |
| ] | |
| } | |
| ], | |
| "metadata": {} | |
| } | |
| ] | |
| } |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment