from pprint import pprint

prenom = "John"  # crée une instance (obj) de type 'str' et l'initialise avec la valeur 'John'
nom = str('Doe') # crée une instance (obj) de type 'str' et l'initialise avec la valeur 'Doe'
adress = str()   # crée une instance (obj) de type 'str'

# list, dict, tuple, set, bool => types primitives

class Fraction: # pour se differencier des types primitifs
    numerateur = 1
    denominateur = 1

    def quotient(self): # self = tiers /quart
        return self.numerateur / self.denominateur

tiers = Fraction() # crée une instance (obj) de type 'Fraction'
tiers.numerateur = 1
tiers.denominateur = 3
quart = Fraction()
quart.numerateur = 1
quart.denominateur = 4

print(tiers.__dict__)
print(quart.__dict__)

# Mapping proxy
# pprint(Fraction.__dict__)
# pprint(tiers.__dict__)
# print(tiers.denominateur)

# 2 points de vue: Fraction (classe) et tiers (objet)
print(Fraction.quotient) # <function Fraction.dire_bonjour at 0x100eec720>
print(tiers.quotient) # <bound method Fraction.dire_bonjour of <__main__.Fraction object at 0x1028937d0>>
# <bound method Fraction.dire_bonjour of tiers>

print(tiers.quotient()) # TypeError: Fraction.dire_bonjour() takes 0 positional arguments but 1 was given
# Les methodes lies aux objets ont besoin de savoir QUI les a appeler
print(quart.quotient())