In [1]:

```
range(5, 10)
```

Out[1]:

In [2]:

```
[1, 2, 3][0] == 1
```

Out[2]:

`[ f(x) for x in ___ ]`

In [3]:

```
[n for n in range(10)]
```

Out[3]:

In [4]:

```
[n^2 for n in range(1,11)]
```

Out[4]:

```
[ f(x) for x in ___ if g(x) ]
```

`f(x)`

is the result`g(x)`

is a boolean function (condition) ### either/or values

Every element will appear in the list, but some with `f1(x)`

values, others with `f2(x)`

values (depending in `g(x)`

)

In [5]:

```
print range(1,21)
[ 3*x+1 if x%2==1 else x//2 for x in range(1,21) ]
```

Out[5]:

`for`

¶Means cross product or Descartes product.

```
[(i,j) for i in ___ for j in ___ ]
```

Goes through `(i, j)`

pairs in the cross product.

Not the same as:

```
[[(i,j) for i in ___ ] for j in ___ ]
```

Because that is a list-of-lists!

In [6]:

```
print([ (i, j) for i in range(5) for j in range(5) ] )
print
print([[ (i, j) for i in range(5)] for j in range(5) ] )
```

inline:

```
f(x) = x^2
```

declaration:

```
def f(x):
return x^2
```

- Mind the colon and the identation!
- The identation decides where to end the function.
- The
`return`

is not necessarily the last line, but nothing is executed after that!

In [7]:

```
x=var('x')
f(x)=x^2
def g(x):
return x^2
def h(x):
return x^2
print('ooh!')
print(f(3), g(3))
print(diff(f,x,1))
print(diff(g(x),x,1))
```

There is a difference between inline and declared functions.

- inline functions can contain only one expression
- inline functions are mathematically funcitions
- declared functions are functions in the
*programming*sense

In [8]:

```
f?
```

inline:

```
f1(x) if g(x) else f2(x)
```

programming:

```
if g(x):
f1(x)
else:
f2(x)
```

Mind the colon and the identation! The `else`

part is optional.

In [9]:

```
def parity(a):
if a%2 == 0:
return "even"
else:
return "odd"
return 0
print(parity(6))
```

If you miss the `return`

then the result is a unique `None`

value.
You cannot miss the return in inline functions.

In [10]:

```
def parity2(a):
if a%2 == 0:
return "even"
else:
print "odd"
'ooh'
print(parity2(5))
```

In [11]:

```
def gcd(a,b):
if (b == 0):
return a
return gcd(b, a%b)
print(gcd(50,15))
```

In [12]:

```
def factorial(n):
if n==0:
return 1
return n*factorial(n-1)
factorial(10)
```

Out[12]:

In [13]:

```
def factorial2(x):
return x*factorial2(x-1)
factorial2(10)
```

The puzzle was invented by the French mathematician Ă‰douard Lucas in 1883. There is a story about an Indian temple in Kashi Vishwanath which contains a large room with three time-worn posts in it, surrounded by 64 golden disks. Brahmin priests, acting out the command of an ancient prophecy, have been moving these disks in accordance with the immutable rules of Brahma since that time. The puzzle is therefore also known as the Tower of Brahma puzzle. According to the legend, when the last move of the puzzle is completed, the world will end.

In [14]:

```
A = [5, 4, 3, 2, 1]
B = []
C = []
def move(n, source, target, auxiliary):
if n > 0:
# move n - 1 disks from source to auxiliary, so they are out of the way
move(n - 1, source, auxiliary, target)
# move the nth disk from source to target
target.append(source.pop())
# Display our progress
print(A, B, C)
# move the n - 1 disks that we left on auxiliary onto target
move(n - 1, auxiliary, target, source)
# initiate call from source A to target C with auxiliary B
move(5, A, C, B)
```