Une introduction à Python 3

Image non disponible


précédentsommairesuivant

2. La calculatrice Python

Image non disponible

Comme tout langage, Python permet de manipuler des données grâce à un vocabulaire de mots réservés et grâce à des types de données — approximation des ensembles de définition utilisés en mathématique.

Ce chapitre présente les règles de construction des identificateurs, les types de données simples (les conteneurs seront examinés au chapitre 4Conteneurs standard) ainsi que les types chaîne de caractères.

Enfin, last but not least, ce chapitre s'étend sur les notions non triviales de variable, de référence d'objet et d'affectation.

2-1. Les modes d'exécution

2-1-1. Les deux modes d'exécution d'un code Python

  • Soit on enregistre un ensemble d'instructions Python dans un fichier grâce à un éditeur (on parle alors d'un script Python) que l'on exécute par une commande ou par une touche du menu de l'éditeur.
  • Soit on utilise l'interpréteur Python embarqué qui exécute la boucle d'évaluation : 
Image non disponible
Figure 2.1 - La boucle d'évaluation de l'interpréteur Python

2-2. Identificateurs et mots clés

2-2-1. Identificateurs

Comme tout langage, Python utilise des identificateurs pour nommer ses objets.

Un identificateur Python est une suite non vide de caractères, de longueur quelconque, formée d'un caractère de début et de zéro ou plusieurs caractères de continuation.

Sachant que :

Les identificateurs sont sensibles à la casse et ne doivent pas être un mot réservé de Python 3 (voir le § « Les mots réservés de Python 3Les mots réservés de Python 3 » ci-dessous).

2-2-2. Style de nommage

Il est important d'utiliser une politique cohérente de nommage des identificateurs. Voici le style utilisé dans ce document(6) :

  • nom_de_ma_variable pour les variables ;
  • NOM_DE_MA_CONSTANTE pour les constantes ;
  • maFonction, maMethode pour les fonctions et les méthodes ;
  • MaClasse pour les classes ;
  • UneExceptionError pour les exceptions ;
  • nom_de_module pour les modules et pour tous les autres identificateurs.

Exemples :

 
Sélectionnez
NB_ITEMS = 12 # UPPER_CASE
class MaClasse : pass # TitleCase
def maFonction() : pass # camelCase
mon_id = 5 # lower_case

Pour ne pas prêter à confusion, éviter d'utiliser les caractères l (minuscule), O et I (majuscules) seuls.

Enfin, on évitera d'utiliser les notations suivantes :

 
Sélectionnez
_xxx # usage interne
__xxx # attribut de classe
__xxx__ # nom spécial réservé

2-2-3. Les mots réservés de Python 3

La version 3.4 de Python compte 33 mots clés :

and

del

from

None

True

as

elif

global

nonlocal

try

assert

else

if

not

while

break

except

import

or

with

class

False

in

pass

yield

continue

finally

is

raise

 

def

for

lambda

return

 

2-3. Notion d'expression

Une expression est une portion de code que l'interpréteur Python peut évaluer pour obtenir une valeur.

Les expressions peuvent être simples ou complexes. Elles sont formées d'une combinaison de littéraux représentant directement des valeurs, d'identificateurs et d'opérateurs.

 
Sélectionnez
>>> id1 = 15.3
>>> id2 = id1 - 13
>>> if id2 > 0:
...     id3 = 7
... else:
...     id3 = -4

2-4. Les types de données entiers

Le type d'un objet Python détermine de quelle sorte d'objet il s'agit.

Python offre deux types entiers standard : int et bool.

2-4-1. Le type int

Le type int n'est limité en taille que par la mémoire de la machine(7).

Les entiers littéraux sont décimaux par défaut, mais on peut aussi utiliser les bases suivantes :

 
Sélectionnez
>>> 2013          # décimal (base 10)
2013
>>> 0b11111011101 # binaire (base 2)
2013
>>> 0o3735        # octal (base 8)
2013
>>> 0x7dd         # hexadecimal (base 16)
2013

2-4-1-a. Opérations arithmétiques

Les principales opérations :

 
Sélectionnez
>>> 20 + 3
23
>>> 20 - 3
17
>>> 20 * 3
60
>>> 20 ** 3
8000
>>> 20 / 3
6.666666666666667
>>> 20 // 3     # division entière
6
>>> 20 % 3      # modulo (reste de la division entière)
2
>>> abs(3 - 20) # valeur absolue
17

Bien remarquer le rôle des deux opérateurs de division :

  • / : produit une division flottante, même entre deux entiers ;
  • // : produit une division entière.

2-4-1-b. Bases usuelles

Un entier écrit en base 10 (par exemple 179) peut être représenté en binaire, octal et hexadécimal en utilisant les syntaxes suivantes :

 
Sélectionnez
>>> 0b10110011 # binaire
179
>>> bin(179)
'0b10110011'
>>> 0o263      # octal
179
>>> oct(179)
'0o263'
>>> 0xB3       # hexadécimal
179
>>> hex(179)
'0xb3'

Les bases arithmétiques

En arithmétique, une base n désigne la valeur dont les puissances successives interviennent dans l'écriture des nombres, ces puissances définissant l'ordre de grandeur de chacune des positions occupées par les chiffres composant tout nombre.

Par exemple : kitxmlcodeinlinelatexdvp57_{n}= \left ( 5\times n^{1}\right )+\left (7\times n^{0} \right )finkitxmlcodeinlinelatexdvp

Certaines bases sont couramment employées :

  • la base 2 (système binaire), en électronique numérique et informatique ;
  • la base 8 (système octal), en informatique ;
  • la base 16 (système hexadécimal), fréquente en informatique ;
  • la base 60 (système sexagésimal), dans la mesure du temps et des angles.

Les changements de base

Un nombre dans une base kitxmlcodeinlinelatexdvpnfinkitxmlcodeinlinelatexdvp donnée s'écrit sous la forme d'addition des puissances successives de cette base.

Exemples :

kitxmlcodelatexdvp\begin{matrix} 57_{16}= \left ( 5\times 16^{1}\right )+\left (7\times 16^{0} \right )=87_{10} \\ 57_{8}= \left ( 5\times 8^{1}\right )+\left (7\times 8^{0} \right )=47_{10} \end{matrix}finkitxmlcodelatexdvp

2-4-2. Le type bool

Principales caractéristiques du type bool(8) :

  • deux valeurs possibles : False, True ;
  • opérateurs de comparaison entre deux valeurs comparables, produisant un résultat de type bool : ==, !=, >, >=, < et <= :
 
Sélectionnez
>>> 2 > 8
False
>>> 2 <= 8 < 15
True
  • opérateurs logiques : not, or et and ;
  • en observant les tables de vérité des opérateurs and et or, on remarque que :
    cette optimisation est appelée « principe du shortcut » ou évaluation au « plus court » :

    • dès qu'un premier membre a la valeur False, l'expression False and expression2 vaudra False. On n'a donc pas besoin d'évaluer expression2,
    • de même dès qu'un premier membre a la valeur True, l'expression True or expression2 vaudra True.
 
Sélectionnez
>>> (3 == 3) or (9 > 24)
True
>>> (9 > 24) and (3 == 3)
False

Les opérateurs booléens de base

En Python les valeurs des variables booléennes sont notées False et True. Les opérateurs sont notés respectivement not, and et or.

Image non disponible

Pour être sûr d'avoir un résultat booléen avec une expression reposant sur des valeurs transtypées, appliquez bool() sur l'expression.

2-5. Les types de données flottants

La notion mathématique de réel est une notion idéale. Ce Graal est impossible à atteindre en informatique.On utilise une représentation interne (normalisée) permettant de déplacer la virgule grâce à une valeur d'exposant variable. On nommera ces nombres des flottants.

2-5-1. Le type float

  • Un float est noté avec un point décimal (jamais avec une virgule) ou en notation exponentielle avec un « e » symbolisant le « 10 puissance » suivi des chiffres de l'exposant. Par exemple :
 
Sélectionnez
2.718
.02
-1.6e-19
6.023e23
  • Les flottants supportent les mêmes opérations que les entiers.
  • Ils ont une précision finie limitée.
  • L'import du module math autorise toutes les opérations mathématiques usuelles. Par exemple :
 
Sélectionnez
>>> import math
>>> print(math.sin(math.pi/4))
0.7071067811865475
>>>> print(math.degrees(math.pi))
180.0
>>>> print(math.factorial(9))
362880
>>> print(math.log(1024, 2))
10.0

2-5-2. Le type complex

  • Les complexes sont écrits en notation cartésienne formée de deux flottants.
  • La partie imaginaire est suffixée par j :
 
Sélectionnez
>>> print(1j)
1j
>>> print((2+3j) + (4-7j))
(6-4j)
>>> print((9+5j).real)
9.0
>>> print((9+5j).imag)
5.0
>>> print((abs(3+4j))) # module
5.0
  • Un module mathématique spécifique (cmath) leur est réservé :
 
Sélectionnez
>>> import cmath
>>> print(cmath.phase(-1 + 0j))
3.141592653589793
>>> print(cmath.polar(3 + 4j))
(5.0, 0.9272952180016122)
>>> print(cmath.rect(1., cmath.pi/4))
(0.7071067811865476+0.7071067811865475j)

2-6. Variables et affectation

2-6-1. Les variables

Dès que l'on possède des types de données, on a besoin des variables pour stocker les données.

En réalité, Python n'offre pas directement la notion de variable, mais plutôt celle de référence d'objet. Tant que l'objet n'est pas modifiable (comme les entiers, les flottants, les chaînes, etc.), il n'y a pas de différence notable entre les deux notions. On verra que la situation change dans le cas des objets modifiables…

Une variable est un identificateur associé à une valeur. En Python, c'est une référence d'objet.

2-6-2. L'affectation

On affecte une variable par une valeur en utilisant le signe = (qui n'a rien à voir avec l'égalité en math !). Dans une affectation, le membre de gauche reçoit le membre de droite ce qui nécessite d'évaluer la valeur correspondant au membre de droite avant de l'affecter au membre de gauche.

 
Sélectionnez
import math
a = 2
b = 7.2 * math.log(math.e / 45.12) - 2*math.pi
c = b ** a

Pour ne pas confondre affectation et égalité, à l'oral, au lieu de dire « a égale 2 », dites « a reçoit 2 ».

La valeur d'une variable, comme son nom l'indique, peut évoluer au cours du temps. La valeur antérieure est perdue :

 
Sélectionnez
>>> a = 3 * 7
>>> a
21
>>> b = 2 * 2
>>> b
4
>>> a = b + 5
>>> a
9

Le membre de droite d'une affectation étant évalué avant de réaliser l'affectation elle-même, la variable affectée peut se trouver en partie droite et c'est sa valeur avant l'affectation qui est utilisée dans le calcul :

 
Sélectionnez
>>> a = 2
>>> a = a + 1 # incrémentation
>>> a
3
>>> a = a - 1 # décrémentation
>>> a
2

2-6-3. Affecter n'est pas comparer !

L'affectation a un effet (elle modifie l'état interne du programme en cours d'exécution), mais n'a pas de valeur (on ne peut pas l'utiliser dans une expression) :

 
Sélectionnez
>>> c = True
>>> s = (c = True) and True
  File "<stdin>", line 1
    s = (c = True) and True
           ^
SyntaxError: invalid syntax

La comparaison a une valeur (de type bool) utilisable dans une expression, mais n'a pas d'effet :

 
Sélectionnez
>>> c = "a"
>>> s = (c == "a") and True
>>> s
True

2-6-4. Les variantes de l'affectation

Outre l'affectation simple, on peut aussi utiliser les formes suivantes :

 
Sélectionnez
>>> v = 4  # affectation simple
>>> v += 2 # affectation augmentée. Idem à v = v + 2 si v est déjà référencé
>>> v
6
>>> c = d = 8 # d reçoit 8 puis c reçoit d (c et d sont des alias)
>>> c, d
(8, 8)
>>> e, f = 2.7, 5.1 # affectation parallèle d'un tuple
>>> (e, f)
(2.7, 5.1)
>>> g, h = ['G', 'H'] # affectation parallèle d'une liste
>>> [g, h]
['G', 'H']
>>> a = 3
>>> a, b = a + 2, a * 2 # toutes les expressions sont évaluées avant la première affectation
>>> a, b
(5, 6)

2-6-5. Représentation graphique des affectations

Dans les schémas de la figure 2.2 les cercles représentent les identificateurs alors que les rectangles représentent les données.

Les affectations relient les identificateurs aux données : si une donnée en mémoire n'est plus reliée, le ramasse-miettes (garbage collector) de Python la supprime automatiquement (car son nombre de références tombe à zéro) :

Image non disponible
Figure 2.2 - L'affectation illustrée.

2-7. Les chaînes de caractères

2-7-1. Présentation

Les chaînes de caractères : le type de données non modifiable str représente une séquence de caractères Unicode.

Non modifiable signifie qu'une donnée, une fois créée en mémoire, ne pourra plus être changée ; toute transformation résultera en la création d'une nouvelle valeur distincte.

Trois syntaxes de chaîne sont disponibles. Remarquez que l'on peut aussi utiliser le ' à la place de ", ce qui permet d'inclure une notation dans l'autre :

 
Sélectionnez
>>> syntaxe1 = "Première forme avec un retour à la ligne \n"
>>> print(syntaxe1)
Première forme avec un retour à la ligne

>>> syntaxe2 = r"Deuxième forme. Chaîne brute\n sans retour à la ligne"
>>> print(syntaxe2)
Deuxième forme. Chaîne brute\n sans retour à la ligne
>>> syntaxe3 = """
Troisième forme
multiligne
  très utile pour
    la documentation
"""
>>> print(syntaxe3)

Troisième forme
multiligne
  très utile pour
    la documentation

>>> guillemets = "L'eau vive"
>>> guillemets
"L'eau vive"
>>> apostrophes = 'Il a dit "gère !"'
>>> apostrophes
'Il a dit "gère !"'

2-7-2. Opérations

 
Sélectionnez
>>> s = "abcde"
>>> len(s)
5
 
Sélectionnez
>>> s1 = "abc"
>>> s2 = "defg"
>>> s3 = s1 + s2
>>> s3
'abcdefg'
 
Sélectionnez
>>> s4 = "Fi!"
>>> s5 = s4 * 3
>>> s5
'Fi! Fi! Fi! '

2-7-3. Fonctions vs méthodes

On peut agir sur une chaîne en utilisant des fonctions (notion procédurale) communes à tous les types séquences ou conteneurs, ou bien des méthodes (notion objet) spécifiques aux chaînes.

  • Exemple d'utilisation de la fonction len() :
 
Sélectionnez
>>> lng = len("abc")
>>> lng
3

Exemple d'utilisation de la méthode upper(). Remarquez la différence de syntaxe : les méthodes utilisent la notation pointée :

 
Sélectionnez
>>> "abracadabra".upper()
"ABRACADABRA"

2-7-4. Méthodes de test de l'état d'une chaîne

Les méthodes suivantes sont à valeur booléenne, c'est-à-dire qu'elles retournent la valeur True ou False.

La notation entre crochets [xxx] indique un élément optionnel que l'on peut donc omettre lors de l'utilisation de la méthode.

La chaîne s = "cHAise basSe" nous servira de test pour toutes les méthodes de cette section.

  • isupper() et islower() : retournent True si la chaîne ne contient respectivement que des majuscules/minuscules :
 
Sélectionnez
>>> s.isupper()
False
  • istitle() : retourne True si seule la première lettre de chaque mot de la chaîne est en majuscule :
 
Sélectionnez
>>> s.istitle()
False
  • isalnum(), isalpha(), isdigit() et isspace() : retournent True si la chaîne ne contient respectivement que des caractères alphanumériques, alphabétiques, numériques ou des espaces :
 
Sélectionnez
>>> s.isalpha()
True
>>> s.isdigit()
False
  • startswith(prefix[, start[, stop]]) et endswith(suffix[, start[, stop]]) : testent si la sous-chaîne définie par start et stop commence respectivement par prefix ou finit par suffix :
 
Sélectionnez
>>> s.startswith('cH')
True
>>> s.endswith('aSSe')
False

2-7-5. Méthodes retournant une nouvelle chaîne

  • lower(), upper(), capitalize() et swapcase() : retournent respectivement une chaîne en minuscules, en majuscules, en minuscules commençant par une majuscule, ou en casse inversée :
 
Sélectionnez
>>> s.lower()
chaise basse
>>> s.upper()
CHAISE BASSE
>>> s.capitalize()
Chaise basse
>>> s.swapcase()
ChaISE BASsE
  • expandtabs([tabsize]) : remplace les tabulations par tabsize espaces (8 par défaut).
  • center(width[, fillchar]), ljust(width[, fillchar]) et rjust(width[, fillchar]) : retournent respectivement une chaîne centrée, justifiée à gauche ou à droite, complétée par le caractère fillchar (ou par l'espace par défaut) :
 
Sélectionnez
>>> s.center(20, '-')
----cHAise basSe----
>>> s.rjust(20, '@')
@@@@@@@@cHAise basSe
  • zfill(width) : complète ch à gauche avec des 0 jusqu'à une longueur maximale de width :
 
Sélectionnez
>>> s.zfill(20)
00000000cHAise basSe
  • strip([chars]), lstrip([chars]) et rstrip([chars]) : suppriment toutes les combinaisons de chars (ou l'espace par défaut) respectivement au début et en fin, au début, ou en fin d'une chaîne :
 
Sélectionnez
>>> s.strip('ce')
HAise basS
  • find(sub[, start[, stop]]) : renvoie l'index de la chaîne sub dans la sous-chaîne start à stop, sinon renvoie -1. rfind() effectue le même travail en commençant par la fin. index() et rindex() font de même, mais produisent une erreur (exception) si la chaîne n'est pas trouvée :
 
Sélectionnez
>>> s.find('se b')
4
  • replace(old, new[, count]) : remplace count instances (toutes par défaut) de old par new :
 
Sélectionnez
>>> s.replace('HA', 'ha')
chaise basSe
  • split(seps[, maxsplit]) : découpe la chaîne en maxsplit morceaux (tous par défaut). rsplit() effectue la même chose en commençant par la fin et striplines() effectue ce travail avec les caractères de fin de ligne :
 
Sélectionnez
>>> s.split()
['cHAise', 'basSe']
  • join(seq) : concatène les chaînes du conteneur seq en intercalant entre chaque élément la chaîne sur laquelle la méthode est appliquée :
 
Sélectionnez
>>> "**".join(['cHAise', 'basSe'])
cHAise**basSe

2-7-6. Indexation simple

Pour indexer une chaîne, on utilise l'opérateur [] dans lequel l'index, un entier signé qui commence à 0 indique la position d'un caractère :

 
Sélectionnez
>>> s = "Rayon X" # len(s) ==> 7
>>> s[0]
'R'
>>> s[2]
'y'
>>> s[-1]
'X'
>>> s[-3]
'n'
Image non disponible
Figure 2.3 - L'indexation d'une chaîne

2-7-7. Extraction de sous-chaînes

Extraction de sous-chaînes. L'opérateur [ ] avec 2 ou 3 index séparés par le caractère : permet d'extraire des sous-chaînes (ou tranches) d'une chaîne.

Image non disponible
Figure 2.4 - Extraction de sous-chaînes

Par exemple :

 
Sélectionnez
>>> s = "Rayon X" # len(s) ==> 7
>>> s[1:4]  # de l'index 1 compris à 4 non compris
'ayo'
>>> s[-2:]  # de l'index -2 compris à la fin
' X'
>>> s[:3]   # du début à l'index 3 non compris
'Ray'
>>> s[3:]   # de l'index 3 compris à la fin
'on X'
>>> s[::2]  # du début à la fin, de 2 en 2
'RynX'
>>> s[::-1] # de la fin au début (retournement)
'X noyaR'

2-8. Les données binaires

2-8-1. Les types binaires

Python 3 propose deux types de données binaires : bytes (non modifiable) et bytearray (modifiable).

 
Sélectionnez
>>> mot = "Animal"
>>> type(mot)
<class 'str'>
>>>
>>> b_mot = b"Animal"
>>> type(b_mot)
<class 'bytes'>
>>>
>>> bmot = bytearray(b_mot)
>>> type(bmot)
<class 'bytearray'>

Une donnée binaire contient une suite de zéro ou plusieurs octets, c'est-à-dire d'entiers non signés sur 8 bits (compris dans l'intervalle [0…255]). Ces types « à la C » sont bien adaptés pour stocker de grandes quantités de données. De plus Python fournit des moyens de manipulation efficaces de ces types.

Les deux types sont assez semblables au type str et possèdent la plupart de ses méthodes. Le type modifiable bytearray possède des méthodes communes au type list.

2-9. Les entrées-sorties

L'utilisateur a besoin d'interagir avec le programme (Fig. 2.5). En mode « console » (on abordera les interfaces graphiques ultérieurement), on doit pouvoir saisir ou entrer des informations, ce qui est généralement fait depuis une lecture au clavier. Inversement, on doit pouvoir afficher ou sortir des informations, ce qui correspond généralement à une écriture sur l'écran.

Image non disponible
Figure 2.5 - Les entrées-sorties

2-9-1. Les entrées

Il s'agit de réaliser une saisie au clavier : la fonction standard input() interrompt le programme, affiche une éventuelle invite à l'écran et attend que l'utilisateur entre une donnée au clavier (affichée à l'écran) et la valide par Image non disponible.

La fonction input() effectue toujours une saisie en mode texte (la valeur retournée est une chaîne) dont on peut ensuite changer le type (on dit aussi transtyper ou cast en anglais) :

 
Sélectionnez
>>> f1 = input("Entrez un flottant :")
Entrez un flottant : 12.345
>>> type(f1)
<class 'str'>
>>> f2 = float(input("Entrez un autre flottant :"))
Entrez un autre flottant : 12.345
>>> type(f2)
<class 'float'>

On rappelle que Python est un langage dynamique (les variables peuvent changer de type au gré des affectations), mais également fortement typé (contrôle de la cohérence des types) :

 
Sélectionnez
>>> i = input("Entrez un entier :")
Entrez un entier : 3
>>> i
'3'
>>> iplus = int(input("Entrez un entier :")) + 1
Entrez un entier : 3
>>> iplus
4
>>> ibug = input("Entrez un entier :") + 1
Entrez un entier : 3
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
TypeError: Can't convert 'int' object to str implicitly

2-9-2. Les sorties

En mode « calculatrice », Python lit-évalue-affiche (Fig. 2.1), mais la fonction print() reste indispensable aux affichages dans les scripts. Elle se charge d'afficher la représentation textuelle des informations qui lui sont données en paramètre, en plaçant un blanc séparateur entre deux informations, et en faisant un retour à la ligne à la fin de l'affichage (le séparateur et la fin de ligne peuvent être modifiés) :

 
Sélectionnez
>>> a, b = 2, 5
>>> print(a, b)
2 5
>>> print("Somme :", a + b)
Somme : 7
>>>> print(a - b, "est la différence")
-3 est la différence
>>> print("Le produit de", a, "par", b, "vaut :", a * b)
Le produit de 2 par 5 vaut : 10
>>> print("On a <", 2**32, a*b, "> cas !", sep="~~~")
On a <~~~4294967296~~~10~~~> cas !
>>> # pour afficher autre chose qu'un espace en fin de ligne :
>>> print(a, end="@")
2@>>> print()

>>>

2-9-3. Les séquences d'échappement

À l'intérieur d'une chaîne, le caractère antislash (\) permet de donner une signification spéciale à certaines séquences de caractères :

Séquence

Signification

\saut_ligne

saut de ligne ignoré (en fin de ligne)

\\

affiche un antislash

\'

apostrophe

\"

guillemet

\a

sonnerie (bip)

\b

retour arrière

\f

saut de page

\n

saut de ligne

\r

retour en début de ligne

\t

tabulation horizontale

\v

tabulation verticale

\N{nom}

caractère sous forme de code Unicode nommé

\uhhhh

caractère sous forme de code Unicode 16 bits

\Uhhhhhhhh

caractère sous forme de code Unicode 32 bits

\ooo

caractère sous forme de code octal

\xhh

caractère sous forme de code hexadécimal

 
Sélectionnez
>>> print("\N{pound sign} \u00A3 \U000000A3")
£ £ £
>>> print("d \144 \x64")
d d d
>>> print(r"d \144 \x64") # la notation r"..." désactive la signification spéciale du caractère "\"
d \144 \x64

précédentsommairesuivant
Voir les détails dans la PEP 8 : « Style Guide for Python », Guido van Rossum et Barry Warsaw.
Dans la plupart des autres langages, les entiers sont codés sur un nombre fixe de bits et ont un domaine de définition limité auquel il convient de faire attention.
Nommé d'après George Boole, logicien et mathématicien britannique du XIXe siècle.

Vous avez aimé ce tutoriel ? Alors partagez-le en cliquant sur les boutons suivants : Viadeo Twitter Facebook Share on Google+   

  

Les sources présentées sur cette page sont libres de droits et vous pouvez les utiliser à votre convenance. Par contre, la page de présentation constitue une œuvre intellectuelle protégée par les droits d'auteur. Copyright © 2015 Kordeo. Aucune reproduction, même partielle, ne peut être faite de ce site et de l'ensemble de son contenu : textes, documents, images, etc. sans l'autorisation expresse de l'auteur. Sinon vous encourez selon la loi jusqu'à trois ans de prison et jusqu'à 300 000 € de dommages et intérêts.