Skip to content

Instantly share code, notes, and snippets.

@Michael0x2a
Last active December 16, 2015 05:08
Show Gist options
  • Save Michael0x2a/5381707 to your computer and use it in GitHub Desktop.
Save Michael0x2a/5381707 to your computer and use it in GitHub Desktop.
A study guide for the PSCSTA programming competition, and a review of some interesting features of Python in general.
{
"metadata": {
"name": "study-guide"
},
"nbformat": 3,
"nbformat_minor": 0,
"worksheets": [
{
"cells": [
{
"cell_type": "markdown",
"metadata": {},
"source": [
"# Study guide\n",
"\n",
"## Basic data types.\n",
"\n",
"These are the basic data types (that will be relevant). They all have their advantages and disadvantages, so be somewhat familiar with them.\n",
"\n",
"### `str` and `unicode`\n",
"\n",
"* If you want to make a large string, don't add them together. Use the ``.join([list_of_strings])` idiom for better performance\n",
"* You can multiply strings: `\"abc\" * 3` results in `\"abcabcabc\"`\n",
"\n",
"### `list`\n",
"* Mutable\n",
"* Can be used as a queue (`a = mylist.pop()` and `mylist.append(a)`)\n",
"* Cannot be used as a dict key\n",
"\n",
"### `tuple`\n",
"* Like a list, except immutable and fixed. No list slicing, popping, or appending\n",
"* Can be used as a dict key\n",
"* To make a tuple, wrap elements in parenthesis: `my_tuple = (a, b)`. For a tuple containing only a single element, use `my_tuple = tuple(a)`\n",
"\n",
"### `dict`\n",
"* Keys must be unique\n",
"* Use the `a in mydict` idiom to see if `a` is a key inside the dict\n",
"* Use `mydict.items()` to get a list/iterator returning a `(key, pair)` tuple. Example:"
]
},
{
"cell_type": "code",
"collapsed": false,
"input": [
"mydict = {'a': 1, 'b': 1, 'c':2}\n",
"for key, pair in mydict.items():\n",
" print key, pair"
],
"language": "python",
"metadata": {},
"outputs": [
{
"output_type": "stream",
"stream": "stdout",
"text": [
"a 1\n",
"c 2\n",
"b 1\n"
]
}
],
"prompt_number": 1
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"* Use `mydict.values()` to get a list of just the pairs.\n",
"* Dicts are unordered.\n",
"\n",
"### `set`\n",
"\n",
"* Like a list, but can be used to find if one set is a subset of another, symmetrical, overlapping, etc. \n",
"* Sets are unordered (unlike lists and tuples).\n",
"\n",
"## List slicing\n",
"\n",
"You access lists like this: `element = mylist[index]`\n",
"\n",
"You get substrings of lists using this syntax: `mylist[start_index : end_index : optional_step]`.\n",
"\n",
"Leaving any of the 3 blank defaults to the start of the list, the end of the list, and a step value of 1, respectively.\n",
"\n",
"Negative numbers wrap around.\n",
"\n",
"Examples:"
]
},
{
"cell_type": "code",
"collapsed": false,
"input": [
"mylist = ['a', 'b', 'c', 'd', 'e', 'f']\n",
"\n",
"print mylist[:]\n",
"print mylist[:3]\n",
"print mylist[3:]\n",
"print mylist[2:4]\n",
"print mylist[2:5:2]\n",
"print mylist[:-1]"
],
"language": "python",
"metadata": {},
"outputs": [
{
"output_type": "stream",
"stream": "stdout",
"text": [
"['a', 'b', 'c', 'd', 'e', 'f']\n",
"['a', 'b', 'c']\n",
"['d', 'e', 'f']\n",
"['c', 'd']\n",
"['c', 'e']\n",
"['a', 'b', 'c', 'd', 'e']\n"
]
}
],
"prompt_number": 2
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## List and dictionary comprehensions\n",
"\n",
"List comprehensions are a great way to take a list, quickly filter through it, and transform it in some manner.\n",
"\n",
"They follow this basic syntax:\n",
"\n"
]
},
{
"cell_type": "code",
"collapsed": false,
"input": [
"my_list = [1, 4, 4, 5, 6]\n",
"print [element for element in my_list]"
],
"language": "python",
"metadata": {},
"outputs": [
{
"output_type": "stream",
"stream": "stdout",
"text": [
"[1, 4, 4, 5, 6]\n"
]
}
],
"prompt_number": 4
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"...where `element` and `my_list` are variables. You can also filter a list by using `if` and `else` conditions:"
]
},
{
"cell_type": "code",
"collapsed": false,
"input": [
"my_list = [1, 4, 4, 5, 6]\n",
"print [element for element in my_list if element > 4 ]\n",
"print [element if element > 4 else False for element in my_list]"
],
"language": "python",
"metadata": {},
"outputs": [
{
"output_type": "stream",
"stream": "stdout",
"text": [
"[5, 6]\n",
"[False, False, False, 5, 6]\n"
]
}
],
"prompt_number": 11
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"As you notice, this is kinda inconsistent. That's because the second example is using Python's ternary operator to filter:"
]
},
{
"cell_type": "code",
"collapsed": false,
"input": [
"a = True\n",
"b = \"Hi\" if a else \"Bye\"\n",
"print b"
],
"language": "python",
"metadata": {},
"outputs": [
{
"output_type": "stream",
"stream": "stdout",
"text": [
"Hi\n"
]
}
],
"prompt_number": 12
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"You can use functions to map one list to another:"
]
},
{
"cell_type": "code",
"collapsed": false,
"input": [
"def square(x):\n",
" return x * x\n",
"\n",
"my_list = [1, 4, 4, 5, 6]\n",
"out = [square(num) for num in my_list]\n",
"print out"
],
"language": "python",
"metadata": {},
"outputs": [
{
"output_type": "stream",
"stream": "stdout",
"text": [
"[1, 16, 16, 25, 36]\n"
]
}
],
"prompt_number": 13
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"You can also use dictionary comprehensions:"
]
},
{
"cell_type": "code",
"collapsed": false,
"input": [
"def square(x):\n",
" return x * x\n",
"\n",
"my_list = [1, 4, 4, 5, 6]\n",
"\n",
"out = {a: square(a) for a in my_list}\n",
"\n",
"second_out = {str(key): key - pair for key, pair in out.items()}\n",
"\n",
"print out\n",
"print second_out"
],
"language": "python",
"metadata": {},
"outputs": [
{
"output_type": "stream",
"stream": "stdout",
"text": [
"{1: 1, 4: 16, 5: 25, 6: 36}\n",
"{'1': 0, '5': -20, '4': -12, '6': -30}\n"
]
}
],
"prompt_number": 17
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Generators and iterators\n",
"\n",
"A key part of Python is its use of iterators and generators.\n",
"\n",
"An iterator is a list-like object: it contains multiple elements, and returns them one after another.\n",
"\n",
"A list is an example of an iterator. A generator is another example of an iterator. However, unlike a list, a generator can only be iterated over once. They don't store all their values in memory, but instead generate values on the fly. This can be significantly less computationally expensive.\n",
"\n",
"There are several ways to make a generator. You can use the `yield` statement and make a function, or use a generator comprehension."
]
},
{
"cell_type": "code",
"collapsed": false,
"input": [
"def squares(start, stop):\n",
" for i in xrange(start, stop):\n",
" yield i**2\n",
" \n",
"alternate_squares = (i**2 for i in xrange(5))\n",
" \n",
"for i in squares(2, 10):\n",
" print i\n",
" \n",
"print ''\n",
"for i in alternate_squares:\n",
" print i"
],
"language": "python",
"metadata": {},
"outputs": [
{
"output_type": "stream",
"stream": "stdout",
"text": [
"4\n",
"9\n",
"16\n",
"25\n",
"36\n",
"49\n",
"64\n",
"81\n",
"\n",
"0\n",
"1\n",
"4\n",
"9\n",
"16\n"
]
}
],
"prompt_number": 20
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"In general, any time you can put in a list, you can use a generator instead, unless you're doing list-slicing or accessing specific members of a list. \n",
"\n",
"## Built-in functions\n",
"\n",
"Here are all of Python's [built-in functions](http://docs.python.org/2/library/functions.html). Here are some particularly useful ones.\n",
"\n",
"* `all(iterable)`: \n",
" Return True if all elements of the iterable are true or if the element is empty.\n",
"* `any(iterable)`: \n",
" Return True if any element of the iterable is true. If the iterable is empty, return False.\n",
"* `chr(num)`: \n",
" Converts a number into its ASCII string. Must be between 0 to 255.\n",
"* `enumerate(iterable, start=0)`: \n",
" Returns a generator yielding tuples containing the index (starting from `start`) and the element from the iterable."
]
},
{
"cell_type": "code",
"collapsed": false,
"input": [
"mylist = ['aaaa', 'bbbb', 'cccc', 'dddd']\n",
"for index, thing in enumerate(mylist):\n",
" print index, thing"
],
"language": "python",
"metadata": {},
"outputs": [
{
"output_type": "stream",
"stream": "stdout",
"text": [
"0 aaaa\n",
"1 bbbb\n",
"2 cccc\n",
"3 dddd\n"
]
}
],
"prompt_number": 22
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"* `getattr(object, name[, default])`: \n",
" Return the value of the named attribute of *object*. Example:"
]
},
{
"cell_type": "code",
"collapsed": false,
"input": [
"class Test(object):\n",
" def __init__(self, foo):\n",
" self.foo = foo\n",
" \n",
" def bar(self):\n",
" return \"Hi \" + self.foo\n",
" \n",
"t = Test(\"doggy\")\n",
"\n",
"print getattr(t, \"foo\")\n",
"print getattr(t, \"bar\")()"
],
"language": "python",
"metadata": {},
"outputs": [
{
"output_type": "stream",
"stream": "stdout",
"text": [
"doggy\n",
"Hi doggy\n"
]
}
],
"prompt_number": 23
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"* `hasattr(object, name)`: \n",
" Like the above, only it returns True if the attribute exists.\n",
"* `len(s)`: \n",
" Returns the length of the sequence\n",
"* `max(iterable)`: \n",
" Returns the largest argument in the iterable\n",
"* `min(iterable)`: \n",
" Returns the smallest element in the iterable\n",
"* `ord(char)`: \n",
" Converts an ASCII char into its corresponding number.\n",
"* `round(number[, digits])`: \n",
" Rounds a number to the number of digits specified (which defaults to zero). The number of digits can be negative.\n",
"* `sum(iterable)`: \n",
" Returns the sum of the elements in the iterable.\n",
"* `type(object)`: \n",
" Returns the type of the object.\n",
"* `zip([iterable, ...])`: \n",
" Sort of splices two or more iterables together."
]
},
{
"cell_type": "code",
"collapsed": false,
"input": [
"x = [1, 2, 3]\n",
"y = ['a', 'b', 'c']\n",
"z = [True, False, None]\n",
"\n",
"print zip(x, y)\n",
"print zip(x, y, z)"
],
"language": "python",
"metadata": {},
"outputs": [
{
"output_type": "stream",
"stream": "stdout",
"text": [
"[(1, 'a'), (2, 'b'), (3, 'c')]\n",
"[(1, 'a', True), (2, 'b', False), (3, 'c', None)]\n"
]
}
],
"prompt_number": 24
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Misc tips and tricks:\n",
"\n",
"### Applying a list or dict to a function\n"
]
},
{
"cell_type": "code",
"collapsed": false,
"input": [
"a = [1, 2, 3]\n",
"b = {'a':4, 'b':5, 'c':6}\n",
"\n",
"def test(a, b, c):\n",
" print a\n",
" print b\n",
" print c\n",
" \n",
"def test2(*args, **kwargs):\n",
" print args\n",
" print kwargs\n",
" \n",
"test(*a)\n",
"print ''\n",
"test2(*a, **b)"
],
"language": "python",
"metadata": {},
"outputs": [
{
"output_type": "stream",
"stream": "stdout",
"text": [
"1\n",
"2\n",
"3\n",
"\n",
"(1, 2, 3)\n",
"{'a': 4, 'c': 6, 'b': 5}\n"
]
}
],
"prompt_number": 26
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"### Deep-copying a list\n",
"\n",
"Doing `var = mylist` does not copy all the elements inside `mylist`. You must use the `copy` module instead."
]
},
{
"cell_type": "code",
"collapsed": false,
"input": [
"class Test(object):\n",
" def __init__(self, name):\n",
" self.name = name\n",
" \n",
"mylist = [Test('Bob'), Test('Sally'), Test('John')]\n",
"\n",
"shallow_copy = mylist\n",
"mylist[0].name = \"Xerxes\"\n",
"\n",
"# The objects inside the list haven't been changed\n",
"print shallow_copy[0].name \n",
"\n",
"import copy\n",
"\n",
"# A copy of the objects inside the list were made\n",
"deep_copy = copy.deepcopy(mylist) \n",
"mylist[0].name = \"Jonathan\"\n",
"print deep_copy[0].name\n",
"print shallow_copy[0].name"
],
"language": "python",
"metadata": {},
"outputs": [
{
"output_type": "stream",
"stream": "stdout",
"text": [
"Xerxes\n",
"Xerxes\n",
"Jonathan\n"
]
}
],
"prompt_number": 28
},
{
"cell_type": "code",
"collapsed": false,
"input": [],
"language": "python",
"metadata": {},
"outputs": []
}
],
"metadata": {}
}
]
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment