Please, rename this notebook before editing!

The Programming Language Python

References

Here are some references to freshen up on concepts:

Python 2 vs Python 3

While there are a number of major differences between the versions the majority of libraries and tools that we are concerned with operate on both. Most changes in Python 3 concern the internal workings and performance. Though, there are some syntax changes, and some operations behave differently. This pages offers a comprehensive look at the key changes: http://sebastianraschka.com/Articles/2014_python_2_3_key_diff.html

We provide both versions on our cluster: the binaries python and python2 for Python 2.7, and python3 for version 3.4.

All assignments are expected to run on Python 2.7

The following has been adopted from https://www.learnpython.org/

Variables and Types

One of the conveniences and pit-falls is that Python does not require to explicitly declare variables before using them. This is common in many other programming languages. Python is not statically typed, but rather follows the object oriented paradigm. Every variable in Python is an object.

However, the values that variables hold have a designated data type.

This tutorial will go over a few basic types of variables.

Numbers

Python supports two types of numbers - integers and floating point numbers. Basic arithmetic operations yield different results for integers and floats. Special attention needs to be given when mixing values of different types within expressions the results might be unexpected.

To define an integer, use the following syntax:


In [ ]:
x = 7+3
print x, type(x)

In [ ]:
print x

In [ ]:
x = (x+5)*0.5
print x, type(x)

In [ ]:
type(x)

To define a floating point number, you may use one of the following notations:


In [ ]:
myfloat = 7.0
print myfloat, type(myfloat)
myfloat = float(42)
print myfloat, type(myfloat)

Arithmetic operations

We can arithmetic operations that are common in many programing languages.

  • +, -, *, /
  • // is a special integer division even if the operands aren't
  • x**y is used for $x^y$
  • n % k calculates the remainder (modulo) of the integer division of n by k

Try it out!


In [ ]:


In [ ]:


In [ ]:
(numerator, denominator) = 3.5.as_integer_ratio()
print numerator, denominator, numerator/denominator, 1.0*numerator/denominator

In [ ]:

Strings

Strings are defined either with a single quote or a double quotes. Many other languages interpret them differently.


In [ ]:
mystring = 'hello'
print(mystring)
mystring = "hello"
print(mystring)

The difference between the two is that using double quotes makes it easy to include apostrophes (whereas these would terminate the string if using single quotes)


In [ ]:
my_String99 = 'Don\'t worry about apostrophes'
print(my_String99)

In [ ]:

Operators

Some the arithmetic operators can be applied to strings, though they have a different interpretation

  • + will concatenate two strings
  • * multiplies a string with an integer, i.e. the result is that many copies of the original string.
  • % has a very special purpose to fill in values into strings

Python provides a large number of operations to manipulate text strings. Examples are given at https://www.tutorialspoint.com/python/python_strings.htm

For the complete documentation refer to https://docs.python.org/2/library/string.html


In [ ]:
3*"u"

String Formatting

Python uses C-style string formatting to create new, formatted strings. The "%" operator is used to format a set of variables enclosed in a "tuple" (a fixed size list), together with a format string, which contains normal text together with "argument specifiers", special symbols like "%s" and "%d".

Some basic argument specifiers you should know: %s - String (or any object with a string representation, like numbers)

%d - Integers

%f - Floating point numbers

%.<number of digits>f - Floating point numbers with a fixed amount of digits to the right of the dot.

%x/%X - Integers in hex representation (lowercase/uppercase)


In [ ]:
7.0/13.0

In [ ]:
print "The magic number is %.2f!" % (7.0/13.0)

In [ ]:
int("3")

In [ ]:
float("6.3")

In [ ]:
int(str(8)*8)/6

In [ ]:

Lists

Lists are construct for holding multiple objects or values of different types (if this makes sense). We can dynamically add, replace, or remove elements from a list.

Usually we iterate through list in order to perform some operations, though, we can also address a specific element by its position (index) in the list.

The + and * operators work on lists in a similar way as they do on strings.

Complete documentation at https://docs.python.org/2/tutorial/datastructures.html


In [ ]:
mylist = [1, 2, "three", ("a", 7)]
print len(mylist)
print mylist

In [ ]:
mylist[0]

In [ ]:
mylist + [7, 8, 8]

In [ ]:
mylist * 2

List Comprehension

This technique comes in handy and is often used.


In [ ]:
power_of_twos = [2**k for k in xrange(0,10)]
print power_of_twos

In [ ]:
[k for k in xrange(0,10)]

In [ ]:
[i*j for i in xrange(1,11) for j in xrange(1,11)]

In [ ]:
[ [i*j for i in xrange(1,11) ] for j in xrange(1,11)]

In [ ]:


In [ ]:


In [ ]:


In [ ]:

Conditions

Python uses boolean variables to evaluate conditions. The boolean values True and False are returned when an expression is compared or evaluated.

Notice that variable assignment is done using a single equals operator "=", whereas comparison between two variables is done using the double equals operator "==". The "not equals" operator is marked as "!=".


In [ ]:
x = 2.0001
print(x == 2) # prints out True
print(x == 3) # prints out False
print(x < 3) # prints out True

The "and", "or" and "not" boolean operators allow building complex boolean expressions, for example:


In [ ]:
name = "John"
age = 23
if name == "John" and age == 23:
    print("Your name is John, and you are also 23 years old.")

if name == "John" or name == "Rick":
    print("Your name is either John or Rick.")

The "in" operator could be used to check if a specified object exists within an iterable object container, such as a list:


In [ ]:
name = "John"
if name in ["John", "Rick"]:
    print("Your name is either John or Rick.")

Python uses indentation to define code blocks, instead of brackets. The standard Python indentation is 4 spaces, although tabs and any other space size will work, as long as it is consistent. Notice that code blocks do not need any termination.

Here is an example for using Python's "if" statement using code blocks:

if <statement is true>:
    <do something>
    ....
    ....
elif <another statement is true>: # else if
    <do something else>
    ....
    ....
else:
    <do another thing>
    ....
    ....

In [ ]:
x = 3

if x == 2:
    print("x equals two!")
    print("x equals two! ... again")   
else:
    print("x does not equal to two.")
print "done?"

A statement is evaulated as true if one of the following is correct: 1. The "True" boolean variable is given, or calculated using an expression, such as an arithmetic comparison. 2. An object which is not considered "empty" is passed.

Here are some examples for objects which are considered as empty: 1. An empty string: "" 2. An empty list: [] 3. The number zero: 0 4. The false boolean variable: False


In [ ]:


In [ ]:


In [ ]:

Loops

There are two types of loops in Python, for and while.

The "for" loop

For loops iterate over a given sequence. Here is an example: primes = [2, 3, 5, 7] for prime in primes: print(prime)

For loops can iterate over a sequence of numbers using the range and xrange functions. The difference between range and xrange is that the range function returns a new list with numbers of that specified range, whereas xrange returns an iterator, which is more efficient. (Python 3 uses the range function, which acts like xrange). Note that the range function is zero based.


In [ ]:
# Prints out the numbers 0,1,2,3,4
for x in range(5):
    print(x)

# Prints out 3,4,5
for x in range(3, 6):
    print(x)

# Prints out 3,5,7
for x in range(3, 8, 2):
    print(x)

"while" loops

While loops repeat as long as a certain boolean condition is met. For example:


In [ ]:
count = 0
while count < 5:
    print(count)
    count += 1  # This is the same as count = count + 1

In [1]:
x


---------------------------------------------------------------------------
NameError                                 Traceback (most recent call last)
<ipython-input-1-401b30e3b8b5> in <module>()
----> 1 x

NameError: name 'x' is not defined

In [8]:
## compute the Greatest Common Denominator (GCD)
a = 18802
b = 401

while a!=b:
    # put smaller number in a
    (a, b) = (a, b) if a<b else (b, a)
    b = b - a

print "The GCD is %d"%a


The GCD is 1

In [37]:
import myfirst

In [39]:
myfirst.gcd(15, 12)


Out[39]:
15

In [ ]:
# %load myfirst.py
#!/usr/bin/env python
def gcd(a,b):
    while a!=b:
        # put smaller number in a
        ##(a, b) = (a, b) if a<b else (b, a) #(a<b)?(a,b):(b,a)
        if b>a:
            (a, b) = (b, a)
        b = b - a
        return a

In [ ]:


In [ ]:


In [ ]:

"break" and "continue" statements

break is used to exit a for loop or a while loop, whereas continue is used to skip the current block, and return to the "for" or "while" statement. A few examples:


In [ ]:
# Prints out 0,1,2,3,4

count = 0
while True:
    print(count)
    count += 1
    if count >= 5:
        break

# Prints out only odd numbers - 1,3,5,7,9
for x in range(10):
    # Check if x is even
    if x % 2 == 0:
        continue
    print(x)

can we use "else" clause for loops?


In [ ]:
# Prints out 0,1,2,3,4 and then it prints "count value reached 5"

count=0
while(count<5):
    print(count)
    count +=1
else:
    print("count value reached %d" %(count))

# Prints out 1,2,3,4
for i in range(1, 10):
    if(i%5==0):
        break
    print(i)
else:
    print("this is not printed because for loop is terminated because of break but not due to fail in condition")

In [ ]:


In [ ]:

Functions and methods

Functions are a convenient way to divide your code into useful blocks, allowing us to order our code, make it more readable, reuse it and save some time. Also functions are a key way to define interfaces so programmers can share their code.

As we have seen on previous tutorials, Python makes use of blocks.

A block is a area of code of written in the format of: block_head: 1st block line 2nd block line

Where a block line is more Python code (even another block), and the block head is of the following format: block_keyword block_name(argument1,argument2, ...) Block keywords you already know are "if", "for", and "while".

Functions in python are defined using the block keyword "def", followed with the function's name as the block's name. For example:


In [9]:
def my_function():
    print("Hello From My Function!")

In [10]:
my_function()


Hello From My Function!

Functions may also receive arguments (variables passed from the caller to the function). For example:


In [15]:
def my_function_with_args(username, greeting):
    print("Hello, "+username+" , From My Function!, I wish you "+greeting)

In [16]:
my_function_with_args("class", "a wonderful day")


Hello, class , From My Function!, I wish you a wonderful day

Functions may return a value to the caller, using the keyword- 'return' . For example:


In [19]:
def sum_two_numbers(a, b):
    return a + b

    print "I'm done"

In [20]:
sum_two_numbers(5,19)


Out[20]:
24

How to call functions


In [ ]:


In [ ]:
def my_function():
    print("Hello From My Function!")

def my_function_with_args(username, greeting):
    print("Hello, %s , From My Function!, I wish you %s"%(username, greeting))

def sum_two_numbers(a, b):
    return a + b

# print(a simple greeting)
my_function()

#prints - "Hello, John Doe, From My Function!, I wish you a great year!"
my_function_with_args("John Doe", "a great year!")

# after this line x will hold the value 3!
x = sum_two_numbers(1,2)

In this exercise you'll use an existing function, and while adding your own to create a fully functional program.

  1. Add a function named list_benefits() that returns the following list of strings: "More organized code", "More readable code", "Easier code reuse", "Allowing programmers to share and connect code together"

  2. Add a function named build_sentence(info) which receives a single argument containing a string and returns a sentence starting with the given string and ending with the string " is a benefit of functions!"

  3. Run and see all the functions work together!


In [ ]:
# Modify this function to return a list of strings as defined above
def list_benefits():
    pass

# Modify this function to concatenate to each benefit - " is a benefit of functions!"
def build_sentence(benefit):
    pass

def name_the_benefits_of_functions():
    list_of_benefits = list_benefits()
    for benefit in list_of_benefits:
        print(build_sentence(benefit))

name_the_benefits_of_functions()

Methods

Methods are very similar to functions with the difference that, typically, a method associated with an objects.


In [23]:
s = "Hello WORLD"
type(s)


Out[23]:
str

In [24]:
s.swapcase()


Out[24]:
'hELLO world'

In [ ]:
len()

In [22]:
3.75.as_integer_ratio()


Out[22]:
(15, 4)

Hint: while typing in the notebook or at the ipython prompt use the [TAB]-key after adding a "." (period) behind an object to see available methods:

  1. Type the name of an already defined object: s
  2. Add a period "." and hit the [TAB]-key: s. $\leftarrow$ This should show a list of available methods to a string.


In [ ]:


In [ ]:

Plotting something

  • Let's put some of our knowledge about lists and functions to use.
  • The following examples will create list of values, and then graph them.
  • We use a module of the Matplotlib library https://matplotlib.org/ The web-site provides detailed documentation and a wealth of examples.

In [25]:
# These two lines are critical to using matplotlib within the noteboook
%matplotlib inline
import matplotlib.pyplot as plt

In [26]:
x = range(10)
x


Out[26]:
[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]

In [27]:
x = [float(i-50)/50.0 for i in range(100)]
x


Out[27]:
[-1.0,
 -0.98,
 -0.96,
 -0.94,
 -0.92,
 -0.9,
 -0.88,
 -0.86,
 -0.84,
 -0.82,
 -0.8,
 -0.78,
 -0.76,
 -0.74,
 -0.72,
 -0.7,
 -0.68,
 -0.66,
 -0.64,
 -0.62,
 -0.6,
 -0.58,
 -0.56,
 -0.54,
 -0.52,
 -0.5,
 -0.48,
 -0.46,
 -0.44,
 -0.42,
 -0.4,
 -0.38,
 -0.36,
 -0.34,
 -0.32,
 -0.3,
 -0.28,
 -0.26,
 -0.24,
 -0.22,
 -0.2,
 -0.18,
 -0.16,
 -0.14,
 -0.12,
 -0.1,
 -0.08,
 -0.06,
 -0.04,
 -0.02,
 0.0,
 0.02,
 0.04,
 0.06,
 0.08,
 0.1,
 0.12,
 0.14,
 0.16,
 0.18,
 0.2,
 0.22,
 0.24,
 0.26,
 0.28,
 0.3,
 0.32,
 0.34,
 0.36,
 0.38,
 0.4,
 0.42,
 0.44,
 0.46,
 0.48,
 0.5,
 0.52,
 0.54,
 0.56,
 0.58,
 0.6,
 0.62,
 0.64,
 0.66,
 0.68,
 0.7,
 0.72,
 0.74,
 0.76,
 0.78,
 0.8,
 0.82,
 0.84,
 0.86,
 0.88,
 0.9,
 0.92,
 0.94,
 0.96,
 0.98]

In [28]:
sin(0.1)


---------------------------------------------------------------------------
NameError                                 Traceback (most recent call last)
<ipython-input-28-21aa1b0e9d32> in <module>()
----> 1 sin(0.1)

NameError: name 'sin' is not defined

In [29]:
from math import *

In [30]:
sin(0.1)


Out[30]:
0.09983341664682815

In [31]:
y = [ xx**2 for xx in x]
y2 = [xx**3 for xx in x]

In [32]:
plt.plot(x, y, label="x^2")
plt.plot(x, y2, label="x^3")
plt.legend(loc="best")
plt.title("Exponential Functions")


Out[32]:
<matplotlib.text.Text at 0x48d4f10>

In [33]:
theta = [ pi*0.02*float(t-50) for t in range (100)]
theta[:10]


Out[33]:
[-3.1415926535897936,
 -3.0787608005179976,
 -3.0159289474462017,
 -2.9530970943744057,
 -2.8902652413026098,
 -2.8274333882308142,
 -2.7646015351590183,
 -2.7017696820872223,
 -2.6389378290154264,
 -2.5761059759436304]

In [34]:
x = [sin(t) for t in theta]
y = [cos(t) for t in theta]

In [36]:
plt.figure(figsize=(6,6))
plt.plot(x,y)
plt.xlim(-3,3)
plt.ylim(-3,3)


Out[36]:
(-3, 3)

Some Fun

Let's draw a picture of a bear in matplotlib. (Watch on YouTube https://www.youtube.com/watch?v=Jt1fSndR2bY)


In [ ]:


In [ ]:


In [ ]:


In [ ]:


In [ ]: