$ cat > hello.asm
SECTION .data
msg: db `Hello world!\n`
len: equ $-msg
SECTION .text
global _start
_start:
mov rax,1
mov rdi,1
mov rsi,msg
mov rdx,len
syscall
mov rax,60
xor rdi,rdi
syscall
$ nasm -f elf64 hello.asm
$ ld hello.o -o hello
$ ./hello
Hello world!
In [1]:
print('Hello World!')
Facts that describe something.
Actions that something can take.
Something that has state and behavior.
A blueprint or specification for objects.
[1, 2, 3]
This is an object
It has state:
It has behavior
In [6]:
# x = 1 / 3
x_numer = 1
x_denom = 3
In [7]:
# y = 3 / 6
y_numer = 3
y_denom = 6
In [9]:
# add x and y
res_numer = (x_numer * y_denom) + (y_numer * x_denom)
res_denom = x_denom * y_denom
res_numer, res_denom
Out[9]:
In [10]:
from fractions import gcd
res_gcd = gcd(res_numer, res_denom)
res_numer = res_numer // res_gcd
res_denom = res_denom // res_gcd
res_numer, res_denom
Out[10]:
In [11]:
def make_rational(numer, denom):
"""Create a pair of integers representing a rational.
Parameters
----------
numer : int
The numerator of the rational.
denom : int
The denominator of the rational.
Returns
-------
rational : tuple
A pair of integers.
"""
return (numer, denom)
In [12]:
# x = 1 / 3
x = make_rational(numer=1, denom=3)
x
Out[12]:
In [13]:
# y = 3 / 6
y = make_rational(3, 6)
y
Out[13]:
numer= and denom=
In [15]:
# res = x + y
res = make_rational((x[0] * y[1]) + (y[0] * x[1]), x[1] * y[1])
res
Out[15]:
In [17]:
res_gcd = gcd(res[0], res[1])
res = make_rational(res[0] // res_gcd, res[1] // res_gcd)
res
Out[17]:
In [21]:
def add_rationals(x, y):
"""Adds two rational numbers.
Parameters
----------
x : tuple
The first rational.
y : tuple
The second rational.
Returns
-------
sum : tuple
The result of x + y
"""
return (x[0] * y[1]) + (y[0] * x[1]), x[1] * y[1]
In [22]:
x = make_rational(1, 3)
y = make_rational(2, 4)
z = make_rational(3, 7)
In [23]:
sum_xy = add_rationals(x, y)
sum_xz = add_rationals(x, z)
sum_yz = add_rationals(y, z)
In [26]:
print(sum_xy)
print(sum_xz)
print(sum_yz)
In [27]:
def reduce_rational(r):
"""Reduce a rational number to the most simple form.
Parameters
----------
r : tuple
A rational.
Returns
-------
reduced : tuple
The most reduced form of r.
"""
g = gcd(r[0], r[1])
return r[0] // g, r[1] // g
In [7]:
x = make_rational(1, 3)
y = make_rational(2, 4)
z = make_rational(3, 7)
In [ ]:
sum_xy = add_rationals(x, y)
sum_xz = add_rationals(x, z)
sum_yz = add_rationals(y, z)
In [ ]:
print(reduce_rational(sum_xy))
print(reduce_rational(sum_xz))
print(reduce_rational(sum_yz))
In [28]:
def rational_to_string(r):
"""Convert a rational number to a human readable
string representation.
Parameters
----------
r : tuple
A rational.
Returns
-------
cs : str
A string representation of r.
"""
return '{numer} / {denom}'.format(numer=r[0], denom=r[1])
In [29]:
x = make_rational(1, 3)
rational_to_string(x)
Out[29]:
In [32]:
class Rational:
"""A rational number.
Parameters
----------
numer : int
The numerator.
denom : int
The denominator.
"""
def __init__(self, numer, denom):
self.numer = numer
self.denom = denom
def add(self, other):
return Rational(
numer=(self.numer * other.denom) + (other.numer * self.denom),
denom=self.denom * other.denom,
)
def eq(self, other):
return self.numer == other.numer and self.denom == other.denom
def reduce(self):
g = gcd(self.numer, self.denom)
return Rational(
numer=self.numer // g,
denom=self.denom // g,
)
def __repr__(self):
return '{numer} / {denom}'.format(numer=self.numer, denom=self.denom)
Rational objects__init__)Rational object how to initialize its stateself represents the state of our objectmake_rationaladd_rationals suffix because we now have some contextothereq behavior for checking equalityreduce_rational__repr__ is also specialrational_to_str
In [35]:
x = Rational(1, 3)
y = Rational(2, 4)
x and y instances of Rational
In [36]:
sum_xy = x.add(y)
sum_xy
Out[36]:
x.add(y) says: "Invoke the add behavior of the x object with y as the second argument"add method of the Rational classself is the state of x
In [37]:
sum_xy.reduce()
Out[37]:
reduce method of sum_xy
In [38]:
x = Rational(1, 2)
y = Rational(2, 4)
print(x)
print(y)
In [39]:
x.eq(y)
Out[39]:
In [40]:
z = Rational(1, 0)
z
Out[40]:
In [47]:
class Rational:
"""A rational number.
Parameters
----------
numer : int
The numerator.
denom : int
The denominator.
"""
def __init__(self, numer, denom):
if denom == 0:
raise ValueError('denom cannot be zero')
g = gcd(numer, denom)
self.numer = numer // g
self.denom = denom // g
def add(self, other):
return Rational(
numer=(self.numer * other.denom) + (other.numer * self.denom),
denom=self.denom * other.denom,
)
def eq(self, other):
return self.numer == other.numer and self.denom == other.denom
def __repr__(self):
return '{numer} / {denom}'.format(numer=self.numer, denom=self.denom)
In [48]:
x = Rational(1, 2)
y = Rational(2, 4)
x, y
Out[48]:
x and y are displayed the same
In [44]:
x.eq(y)
Out[44]:
In [45]:
z = Rational(1, 0)
In [55]:
class Integer(Rational):
"""A ratio whose denominator is 1.
Parameters
----------
value : int
The value of this integer.
"""
def __init__(self, value):
super().__init__(value, 1)
self.is_odd = bool(value & 1)
self.is_even = not self.is_odd
def add(self, other):
if isinstance(other, Integer):
return Integer(self.numer + other.numer)
else:
return super().add(other)
def __repr__(self):
return str(self.numer)
The (Rational) here means that Integer is a subclass of Rational
Be default, we get all of the behavior of Rational
We are overriding the initialization behavior
__init__is_even and is_odd
Do the same with add
Still reference the original add
Notice we didn't change eq
eq just fine
In [56]:
r = Rational(1, 2)
n = Integer(1)
print(isinstance(r, Rational))
print(isinstance(n, Integer))
r be a Rationaln be an Integerr is an instance of Rational -> r is a Rationaln is an instance of Integer -> n is an Integer
In [52]:
print(isinstance(n, Rational))
print(isinstance(r, Integer))
because Integer is a subclass of Rational, n is a Rational
subclassing is a directional relationship
r does not become an Integer
In [63]:
n.is_even
Out[63]:
In [59]:
n.is_odd
Out[59]:
In [60]:
n.eq(r)
Out[60]:
In [61]:
n.eq(Integer(1))
Out[61]:
eq behavior.Rational
In [72]:
class Natural(Integer):
"""An integer that is greater than zero.
Parameters
----------
value : int
The value of the natural.
"""
def __init__(self, value):
if value <= 0:
raise ValueError('value must be greater than zero')
super().__init__(value)
def factorial(self):
fac = 1
for n in range(2, self.numer + 1):
fac *= n
return fac
IntegersRationalsfactorial as a method of Natural.
In [79]:
from flask.views import MethodView
class HelloEndpoint(MethodView):
"""An endpoint handler greets the user.
"""
def get(self):
return 'hello from my new webserver'
MethodViewMethodView by adding our own get behaviorMethodView knows what to do with this.
In [80]:
from flask import Flask
app = Flask('my_app')
app.add_url_rule('/hello', view_func=HelloEndpoint.as_view('hello'))
Flask class from flaskFlask/hello endpoint
In [21]:
class LoggingRestEndpoint(HelloEndpoint):
def get(self):
print('logging: get')
return super().get()
MethodView class