\thumb

%%% 01

\begin{qcm}{Listes, tuples et dictionnaires}{5} % titre , temps
Pour chacune des questions suivantes, une des propositions est exacte.

Laquelle ?

\begin{questions}
\item Si on définit la variable \texttt{lieux} par :
\begin{center}
\texttt{lieux = ["Ville" , "Campagne" , "Forêt"]},
\end{center}
alors:
\begin{questions}
\item \og Ville \fg{}  est :

\choix{} un index;

\choix{} un item.

\item la variable \texttt{lieux} est :\resetchoix

\choix{} une liste;

\choix{} un tuple.

\choix{} un dictionnaire
\end{questions}

\item Si on définit la variable \texttt{couleur} par :
\begin{center}
\texttt{couleur = [ "bleu" , "vert" , "rouge" , "marron" ]},
\end{center}
alors :\resetchoix

\choix{} l'index de \texttt{couleur} est 5;

\choix{} l'index de \og vert \fg{} est \og 2 \fg;

\choix{} l'index de \og marron \fg{} est \og 3 \fg.

\item Si \texttt{liste = ['0','0','1','1','1','2','0','1','2','3']} alors \texttt{liste.count(1)} vaut :\resetchoix

\choix{} 0

\choix{} 3

\choix{} 4

\item Si \texttt{lettres = ["a","b","c","c","d"]} et si on écrit ensuite\linebreak \og \texttt{lettres.append('c')} \fg, que vaut \texttt{len(lettres)} ?\resetchoix

\choix{} 3

\choix{} 4

\choix{} 5

\choix{} 6
\end{questions}
\end{qcm}

\begin{corrige}
\begin{questions}
\item
\begin{questions}
\item Réponse \choix[b]. Il s'agit ici d'un item. L'index de \og Ville \fg{} est \og 0 \fg.
\item Réponse \choix[a]. Il s'agit d'une liste.
\end{questions}

\item Réponse \choix[c]. En effet, l'indexation commence à \og 0 \fg{} donc l'index de \og vert \fg{}  est \og 1 \fg{} (et non \og 2 \fg). Quant à la première proposition (\og l'index de \texttt{couleur} est 5 \fg), elle n'a pas de sens car une liste n'a pas d'index. Seuls les items ont un index.

\item Réponse \choix[a]. En effet, \texttt{liste} est une liste de chaînes de caractères. Or, \texttt{liste.count(1)} demande le nombre d'occurrences du nombre 1 (et non de la chaîne \og 1 \fg). Comme il n'y a pas de nombres dans \texttt{liste}, l'instruction renvoie la valeur : 0.

\item Réponse \choix[d]. En effet, en tapant \og \texttt{lettres.append('c')} \fg, on ajoute un item à la liste \texttt{lettres}. Comme il y en avait 5, il y en a désormais 6.

De plus, l'instruction \texttt{len(lettre)} donne la longueur de la liste, c'est-à-dire le nombres d'items de la liste.
\end{questions}
\end{corrige}

%%% 02

\newpage

\begin{qcm}{Traitement de données}{5} % titre , temps
Pour chacune des questions suivantes, une seule des propositions faites est exacte. Trouvez-la.

\begin{questions}
\item Pour construire une table de 7 lignes et 7 valeurs remplie de 1, on utilise la syntaxe :

\choix \texttt{[1]*7 for i in range(7)}

\choix \texttt{for i in range(7) [1]*7}

\choix \texttt{[[1]*7 for i in range(7)]}

\choix \texttt{[for i in range(7) [1]*7]}

\item \resetchoix Après avoir appelé le module \texttt{csv} de Python, pour importer un fichier CSV dans une table nommée \texttt{table}, on utilise la syntaxe :

\choix \texttt{open('fichier.csv'):}

\qquad\qquad\texttt{data=list(csv.reader('contact.csv'))}

\choix \texttt{open('fichier.csv') as csvfile:}

\qquad\qquad\texttt{data=list(csv.reader(csvfile))}

\choix \texttt{with open('fichier.csv'):}

\qquad\qquad\texttt{data=list(csv.reader('contact.csv'))}

\choix \texttt{with open('fichier.csv') as fic:}

\qquad\qquad\texttt{data=list(csv.reader(fic))}

\item \resetchoix Disposant d'une table nommée \texttt{table} composée uniquement de nombres entiers, rechercher la présence de la valeur 7 peut s'écrire :

\choix \texttt{if 7 in table: <instructions> }

\choix \texttt{for i in table: if 7 in i: <instructions>}

\choix \texttt{for i in table: if 7 in table: <instructions>}

\choix \texttt{for i in table: for j in i: if 7 in j: <instructions>}

\item \resetchoix Une fonction lambda peut être définie par:

\choix \texttt{f = lambda x : x*x+x+1}

\choix \texttt{f : lambda x = x*x+x+1}

\choix \texttt{f : lambda x : x*x+x+1}

\choix \texttt{f = lambda x = x*x+x+1}
\end{questions}
\end{qcm}

\begin{corrige}
\begin{questions}
\item Réponse \choix[c]. Nous souhaitons construire une table donc il doit y avoir deux paires de crochets; ainsi, les réponses \choix[a] et \choix[b] sont impossibles. 

De plus, la construction des lignes s'écrit avant la boucle \og for \fg. La réponse \choix[d] est alors incorrecte.

\item Réponse \choix[d]. La syntaxe commence nécessairement par \og with open \fg{} donc les réponses \choix[a] et \choix[b] sont incorrectes. De plus, après avoir ouvert le fichier CSV, on lui donne un alias avec la syntaxe \og as ... \fg; la réponse \choix[c] est alors incorrecte car il n'y a pas d'alias après l'ouverture du fichier. Cet alias est utilisé ensuite dans la fonction\linebreak \texttt{csv.reader(<mon alias>)}. Dans la réponse correcte, l'alias utilisé est \og fic \fg{} (dans le cours, l'alias utilisé est \og csvfile \fg, mais on peut prendre l'alias que l'on veut).

\enlargethispage*{1em}
\item Réponse \choix[b]. En effet, la réponse \choix[a] ne peut pas être correcte car les items de \texttt{table} sont des listes et non des nombres; par conséquent, si on souhaite tester les items de la table, ce test doit concerner des listes et non des nombres. Par exemple, \og \texttt{if [1,2,3] in table} \fg{} est correct (si on sait que les items de \texttt{table} sont des listes à 3 colonnes).

Pour les mêmes raisons, la réponse \choix[c] n'a pas de sens (car il y a toujours le test \og \texttt{if 7 in table} \fg).

Quant à la réponse \choix[d], elle aurait pu avoir un sens si elle avait été écrite ainsi : 
\begin{center}
\texttt{for i in table: for j in i: if 7 == j: <instructions>}
\end{center}
Mais avec \og \texttt{in} \fg{} à la place de \og \texttt{==} \fg, elle n'a plus de sens.

\item Réponse \choix[a]. On définit une fonction \texttt{f} en la nommant puis en disant à quoi elle est égale (on met donc le signe \og = \fg{} juste après son nom, suivi de \og lambda \fg{} et de la (ou des) variable(s). Ensuite, on définit l'expression de l'image après avoir écrit \og : \fg.
\end{questions}
\end{corrige}


%%% 03

\newpage

\begin{vf}{Listes, tuples et dictionnaires}{5} % titre , temps

Les affirmations suivantes sont elles vraies ou fausses ?

\begin{questions}
\item Les données de la variable \texttt{individu = ('Mélusine','Enfaillite')} sont modifiables.

\item Si \texttt{phrase = "Un être humain est une machine sophistiquée."} alors \texttt{phrase.split(' ')} est une liste à sept items.

\item L'instruction \og \texttt{mots.tri()} \fg{} permet de mettre les items de la liste \texttt{mots} dans l'ordre alphabétique.
\end{questions}
\end{vf}

\begin{corrige}
\begin{questions}
\item L'affirmation est \textit{fausse}. Telle que définie, la variable \texttt{individu} est un tuple, donc par définition, on ne peut pas modifier les données stockées.

\item L'affirmation est \textit{vraie}. En effet, la fonction \texttt{split} sépare une chaîne de caractères selon le caractère informé entre les parenthèses et chaque partie est stockée dans une liste.

Le caractère selon lequel on souhaite couper la variable \texttt{phrase} étant l'espace, on compte le nombre de mots séparés par un espace : il y en a sept. Donc la liste créée a sept items.

\item L'affirmation est \textit{fausse}. La fonction \texttt{tri()} n'existe pas. En revanche, \texttt{mots.sort()} range les items dans l'ordre alphabétique.
\end{questions}
\end{corrige}

%%%%%%%%%%%%%%%%%%%% LISTES

\sectionnn{Listes}

%%% 04

\begin{exo}{Un air de déjà-vu}{\null}{1}{5} 
Quel rôle a le programme suivant ?

\begin{listing}{}{03-04.py}\end{listing}
\end{exo}

\begin{corrige}
Voyons étape par étape ce que fait le programme :

\begin{itemize}
\item la ligne 1 demande d'entrer un nom et un prénom, que l'on stocke dans la variable \texttt{nom\_prenom};

\item \texttt{nom\_prenom.split(' ')} sépare la variable \texttt{nom\_prenom} de part et d'autre du caractère \og espace \fg{} -- à l'aide de la fonction \texttt{split} -- et donne une liste de deux items (le nom et le prénom). Donc \texttt{nom\_prenom.split(' ')[0]} représente le premier item, donc le nom, stocké dans la variable \texttt{nom};

\item \texttt{nom[0]} représente le premier caractère de la chaîne \texttt{nom} donc \texttt{nom[0].upper()} représente l'initiale de \texttt{nom} en majuscule;

\item les deux lignes suivantes définissent de la même façon l'initiale en majuscule du prénom.
\end{itemize}

Ainsi, les variables \texttt{a} et \texttt{b} renferment les initiales en majuscules du nom et du prénom, variables affichées par le programme.
\newpage
\end{corrige}

%%% 05

\begin{exo}{Stocker des valeurs}{\null}{1}{10} 
On considère le nombre :
\[ A = n^2-2n+3,\qquad n\in\N. \]
\'Ecrire un programme qui stocke dans une liste \texttt{valeurs} les différentes\linebreak valeurs de $A$ pour $n$ allant de 0 à 10, et qui affiche la liste.
\end{exo}

\begin{corrige}
Un programme possible est le suivant :

\begin{listing}{}{03-05.py}\end{listing}

\Par

Explications :

\begin{itemize}
\item on commence par définir la variable \texttt{valeurs} comme une liste (vide);

\item on parcourt ensuite les nombres entiers de 0 à 10 à l'aide de \texttt{range(11)} : ne pas oublier que la fonction \texttt{range(a)} commence à 0 et finit à $a-1$. C'est la raison pour laquelle il faut aller jusqu'à 11 pour afficher tous les nombres $A$ jusqu'à $n=10$;

\item on utilise ensuite la méthode \texttt{extend} pour ajouter les différentes valeurs de $A$ en fonction de $n$. 

\begin{attention}
On a ici utilisé des crochets à l'intérieur de la méthode \texttt{extend} car \texttt{n*n-2*n+3} est considéré comme un nombre de classe \textit{int}, et non comme un item de liste. Donc sans crochets, Python renvoie l'erreur : \og \texttt{TypeError: 'int' object is not iterable} \fg. 
\end{attention}
\end{itemize}
\end{corrige}

%%% 06

\newpage

\begin{exo}{Manipulations simples}{\null}{1}{10} 
\'Ecrire un programme Python qui permet de :
\begin{itemize}
\item définir une liste (nommée \texttt{liste}) contenant les nombres : 45, 17, 89, 38, 10 et 74 dans cet ordre;
\item trier et afficher la liste ainsi obtenue;
\item ajouter l'élément \og 12 \fg{} à la liste et afficher la liste;
\item renverser et afficher la liste;
\item afficher l'indice de l'élément \og 10 \fg;
\item enlever l'élément \og 38 \fg{} et afficher la liste;
\item afficher la sous-liste du 2\ieme{} au 3\ieme{} élément;
\item afficher la sous-liste du début au 2\ieme{} élément;
\item afficher la sous-liste du 3\ieme{} élément à la fin de la liste;
\item afficher le dernier élément en utilisant un indiçage négatif.
\end{itemize}
\end{exo}

\begin{corrige}
On commence par initialiser la liste :
\begin{listing}{}{03-06-01.py}\end{listing}

\Par

Ensuite, on trie la liste et on affiche le résultat :
\begin{listing}{}{03-06-02.py}
Retourne: [10, 17, 38, 45, 74, 89]\end{listing}

\Par

On ajoute l'élément \og 12 \fg{} à la liste et on affiche la nouvelle liste:
\begin{listing}{}{03-06-03.py}
Retourne : [10, 17, 38, 45, 74, 89, 12]
\end{listing}

\Par

On inverse la liste et on affiche le résultat:
\begin{listing}{}{03-06-04.py}
Retourne : [12, 89, 74, 45, 38, 17, 10]
\end{listing}

\Par

On affiche l'indice de l'élément \og 10 \fg:
\begin{listing}{}{03-06-05.py}
Retourne : 6
\end{listing}

\Par

On enlève l'élément \og 38 \fg{}  on on affiche le résultat:
\begin{listing}{}{03-06-06.py}
Retourne : [12, 89, 74, 45, 17, 10]
\end{listing}

\Par

On affiche maintenant la sous-liste du 2\ieme au 3\ieme élément:
\begin{listing}{}{03-06-07.py}
Retourne : [89, 74]
\end{listing}

\Par

On affiche la sous-liste du début au 2\ieme élément:
\begin{listing}{}{03-06-08.py}
Retourne : [12, 89]
\end{listing}

\Par

On affiche la sous-liste du 3\ieme élément au dernier:
\begin{listing}{}{03-06-09.py}
[74, 45, 17, 10]
\end{listing}

\Par

On affiche le dernier élément en utilisant un indice négatif:
\begin{listing}{}{03-06-10.py}
Retourne : 10
\end{listing}
\newpage
\end{corrige}

%%% 07

\begin{exo}{Construction d'une liste spéciale}{\null}{1}{10} 
Soit $n$ une valeur entière saisie par l'utilisateur.trice.
\begin{questions}
\item \'Ecrire un programme qui permet de construire une liste de la forme :
\begin{center}
\ttfamily
[1,1,1,2,1,3,1,4,1,5,1,6,...,1,n]
\end{center}

\item \'Ecrire un programme qui permet de construire une liste de la forme :
\begin{center}
\ttfamily
[1,1,2,1,2,3,1,2,3,4,1,2,3,4,5,...,1,2,3,...,n]
\end{center}
\end{questions}
\end{exo}

\begin{corrige}
\begin{questions}
\item \raisebox{-0.5\totalheight+3mm}{\begin{minipage}{\linewidth}\begin{listing}{}{03-07-01.py}\nathanliveProgWithoutText\end{listing}\end{minipage}}

\Par

\item \raisebox{-0.5\totalheight+3mm}{\begin{minipage}{\linewidth}\begin{listing}{}{03-07-02.py}\nathanliveProgWithoutText\end{listing}\end{minipage}}
\end{questions}
\end{corrige}

%%% 08

\begin{exo}{La fonction range}{\null}{1}{15} 
\begin{questions}
\item \'Ecrire un programme qui :
\begin{itemize}
\item définit une liste (nommée \texttt{liste}) contenant tous les entiers de 1 à 10 à l'aide de la fonction \texttt{range};
\item calcule et affiche la somme des éléments de \texttt{liste} et stocke le résultat dans la variable \texttt{somme};
\item calcule et affiche la moyenne de ces nombres, en utilisant la variable \texttt{somme}.
\end{itemize}
\enlargethispage*{2em}
\item \'Ecrire un programme qui permet de calculer et d'afficher, à l'aide de la fonction \texttt{range} et d'une boucle, les sommes :
\[ 
1 + \frac{1}{2^2} + \frac{1}{3^2} + \cdots + \frac{1}{100^2}, \quad 1 + \frac{1}{2^2} + \frac{1}{3^2} + \cdots + \frac{1}{\numprint{1000}^2} \]
\[ \text{et}\qquad 1 + \frac{1}{2^2} + \frac{1}{3^2} + \frac{1}{4^2} + \cdots + \frac{1}{\numprint{10000}^2}. \]

\item En utilisant la fonction range, écrire un programme qui calcule la somme :
\[
50\times1+52\times2+54\times3+56\times4+58\times5+\cdots+100\times25.
\]
\end{questions}
\end{exo}

\begin{corrige}
\begin{questions}
\item \raisebox{-0.5\totalheight+3mm}{\begin{minipage}{\linewidth}\begin{listing}{}{03-08-01.py}\nathanliveProgWithoutText\end{listing}\end{minipage}}

\newpage

\item \raisebox{-0.5\totalheight+3mm}{\begin{minipage}{\linewidth}\begin{listing}{}{03-08-02.py}\nathanliveProgWithoutText\end{listing}\end{minipage}}

\Par

L'utilisation de la boucle \og \texttt{for n in [100,1000,10000]} \fg{} nous a permis d'écrire moins de lignes qu'en utilisant \og {\small\texttt{for\hspace*{-1mm} i\hspace*{-1mm} in\hspace*{-1mm} range(1,100)}} \fg,  \og \texttt{for i in range(1,1000)} \fg{} et \og \texttt{for i in range(1,10000)} \fg.

\item \raisebox{-0.5\totalheight+3mm}{\begin{minipage}{\linewidth}\begin{listing}{}{03-08-03.py}\nathanliveProgWithoutText\end{listing}\end{minipage}}
\end{questions}
\end{corrige}



%%% 09

\begin{exo}{Créer une liste à partir de deux}{\null}{2}{10} 
On donne les chaînes de caractères :
\begin{center}
\ttfamily
chaine1 = "abc" \quad \text{et} \qquad chaine2 = "de".
\end{center}

\'Ecrire un programme permettant de créer la liste  :
\begin{center}
\texttt{['ad', 'ae', 'bd', 'be', 'cd', 'ce'] }
\end{center}

à partir des chaînes \texttt{chaine1} et \texttt{chaine2}.

\Par

\textit{Indication :} on pourra utiliser deux boucles imbriquées.
\end{exo}

\begin{corrige}
\begin{listing}{}{03-09.py}\nathanliveProgWithoutText\end{listing}

\Par\enlargethispage*{\baselineskip}

Explications :

\begin{itemize}
\item on commence par définir les chaînes de caractères, et on définit la liste comme étant vide afin de pouvoir y ajouter des items;

\item on parcourt d'abord la chaîne \texttt{chaine1} avec la boucle \texttt{for i in chaine1};

\item pour chaque lettre de \texttt{chaine1}, on parcourt la chaîne \texttt{chaine2} avec la boucle \texttt{for j in chaine2};

\item à ce stade, \texttt{i} représente un caractère de \texttt{chaine1} et \texttt{j}, un caractère de \texttt{chaine2}. On les concatène avec l'instruction \texttt{i+j} et on insère le résultat dans \texttt{liste} avec l'instruction \texttt{liste.append(i+j)}. 
\end{itemize}
\end{corrige}

%%% 10

\begin{exo}{Une histoire de nombres premiers}{\null}{2}{15}
Un théorème mathématique dit qu'un nombre $n$ est premier si il n'existe pas de diviseurs de $n$ inférieurs ou égaux à $\sqrt{n}$.

\Par\enlargethispage*{\baselineskip}

Voici un programme qui définit une fonction \texttt{ensemble} :

\begin{listing}{}{03-10.py}\end{listing}

\begin{questions}
\item Quand on tape \og ensemble(5) \fg, quel est le type de la variable affichée ?

\item Que représente \texttt{ensemble(n)} ?
\end{questions}
\end{exo}

\begin{corrige}
\enlargethispage*{4em}
\begin{questions}
\item La fonction \texttt{ensemble} retourne une variable \texttt{e} définie initialement par \texttt{e = []}. Il s'agit donc d'une liste.

\Par

Ainsi, \texttt{ensemble(10)} est une liste.

\item Analysons pas à pas la fonction \texttt{ensemble} :

\begin{itemize}
\item on commence par définir la variable \texttt{e} comme étant une liste (vide);

\item ensuite, on parcourt les nombres entiers de 2 à $n$;

\item on initialise \texttt{j} à 2 et \texttt{prem} à \textit{True} pour chaque \texttt{i} avant de tester la condition \og \texttt{j <= i**5} \fg;

\item \texttt{i**0.5} signifie que l'on calcule la racine carrée de \texttt{i}; donc la boucle \og \texttt{while j <= i**0.5} \fg{} signifie que l'on va exécuter les instructions suivantes si \texttt{j} est inférieur ou égal à la racine carrée de \texttt{i};

\item \texttt{i\%j} représente le reste de la division euclidienne de \texttt{i} par \texttt{j}; ainsi, le test \texttt{if i\%j == 0} revient à tester si \texttt{j} divise \texttt{i}. Dans ce cas, la variable booléenne \texttt{prem} passe à \textit{False} et on arrête la boucle \textit{While} (avec \texttt{break}). Dans le cas contraire, on incrémente \texttt{j} (\texttt{j += 1});

\item après la boucle \textit{While}, on teste la valeur de \texttt{prem} : si elle est égale à \textit{True}, on ajoute la valeur de \texttt{i} à la liste \texttt{e}.
\end{itemize}

Cette fonction teste donc tous les $j\leqslant\sqrt{i}$ pour savoir s'ils sont diviseurs de $i$ et si tel n'est pas le cas, le booléen \texttt{prem} vaut \textit{True}, et ce pour toutes les valeurs de $i$ allant de 1 à $n$.

\Par

D'après le théorème de mathématiques cité dans l'énoncé, la fonction \texttt{ensemble(n)} construit la liste des nombres premiers de 2 à $n$.
\end{questions}
\end{corrige}


%%% 11

\begin{exo}{Définition de matrices}{\null}{3}{15} 
\enlargethispage*{3em}
On considère la matrice :
\[
I_n = \begin{pmatrix}
1 & 0 & 0 & \cdots & 0 & 0\\
0 & 1 & 0 & \cdots & 0 & 0\\
0 & 0 & 1 & \cdots & 0 & 0\\
0 & 0 & 0 & \ddots & 0 & 0\\
0 & 0 & 0 & \cdots & 1 & 0\\
0&0&0&\cdots&0&1
\end{pmatrix}
\]
Elle est constituée de $n$ lignes et $n$ colonnes, $n\geqslant2$, où tous les coefficients sont égaux à 0 sauf sur sa diagonale, où il sont égaux à 1.
\newpage
\'Ecrire un programme permettant :
\begin{itemize}
\item de construire une liste par compréhension représentant la matrice nulle, c'est-à-dire la matrice ne contenant que des 0;
\item de construire une liste représentant la matrice $I_n$, pour une valeur de $n$ entrée par l'utilisateur.trice.
\end{itemize}
\end{exo}

\begin{corrige}
\begin{listing}{}{03-11.py}\nathanliveProgWithoutText\end{listing}
\end{corrige}



\sectionnn{Tuples}

%%% 12

\begin{exo}{Pythagore à la rescousse}{\null}{1}{5} 
On souhaite définir une fonction \texttt{is\_square(t)} admettant un triplet \texttt{t} pour argument, ce triplet contenant la longueur des trois côtés d'un triangle.

\begin{questions}
\item Compléter le programme suivant afin qu'il vérifie si le triangle est\linebreak rectangle ou non.

\begin{listing}{}{03-12-01.py}\end{listing}

\item L'utilisation d'un triplet pour argument de cette fonction vous semble-t-elle judicieuse ? Dans la négative, proposer un autre type d'argument et les modifications à apporter au programme précédent.
\end{questions}
\end{exo}

\begin{corrige}
\begin{questions}
\item \raisebox{-0.5\totalheight+3mm}{\begin{minipage}{\linewidth}\begin{listing}{}{03-12-02.py}\nathanliveProgWithoutText\end{listing}\end{minipage}}

\begin{Remarque}
dans la mesure où la fonction \texttt{sort()} n'est pas disponible pour les tuples, on ne peut pas trier les items et on est donc obligé de tester les trois égalités (au cas où les côtés ne seraient pas dans l'ordre croissant).
\end{Remarque}

\item À la vue de la remarque faite à la question précédente, l'utilisation d'un triplet n'est pas judicieuse ici. Il serait préférable d'utiliser une liste afin de pouvoir trier les mesures dans l'ordre croissant et minimiser les conditions :

\Par

\begin{listing}{}{03-12-03.py}\nathanliveProgWithoutText\end{listing}
\end{questions}
\end{corrige}

%%% 13

\begin{exo}{Racines d'un trinôme}{\null}{1}{10} 
On considère un trinôme $P(x)=ax^2+bx+c$, où $a\neq0$.
\enlargethispage*{4em}

Compléter le programme suivant afin que la fonction \texttt{racines(coefs)}\linebreak admette un triplet \texttt{coefs = (a, b, c)} pour argument, et retourne un tuple dont le premier argument est le nombre de racines de $P$ et où les autres arguments sont les valeurs des éventuelles racines.

\begin{listing}{}{03-13-01.py}\end{listing}
\end{exo}

\begin{corrige}
\enlargethispage*{3em}
\begin{listing}{}{03-13-02.py}\nathanliveProgWithoutText\end{listing}
\newpage
\end{corrige}

%%% 14

\begin{exo}{Inventaire et tri}{\null}{2}{15} 
Voici un début de programme :

\begin{listing}{}{03-14-01.py}\end{listing}

\Par

Compléter ce programme afin qu'il affiche le tri souhaité, c'est-à-dire une liste où les noms de fruits sont triés dans l'ordre alphabétique pour le choix~2, ou une liste où les quantités sont triées dans l'ordre croissant pour le choix~1.

\Par

\textit{Indications : } pour le tri numérique, on pourra construire une liste\linebreak \texttt{epicerie\_inverse} où les items sont des tuples de la forme (quantité , fruit).
\end{exo}

\begin{corrige}
\begin{listing}{}{03-14-02.py}\nathanliveProgWithoutText\end{listing}

\Par

Pour le tri alphanumérique, il n'y a aucun problème : la fonction \texttt{sort} fait le travail. 

En revanche, pour trier suivant le deuxième argument des tuples, c'est plus compliqué, d'où l'idée de construire une autre liste en inversant les arguments des tuples.
\newpage
\end{corrige}

%%% 15

\begin{exo}{Minimum, maximum et moyenne}{\null}{2}{15} 
\'Ecrire une fonction \texttt{min\_max\_moy} admettant une liste comme argument et renvoyant la valeur minimum, la valeur maximum et la moyenne des\linebreak valeurs de la liste sous forme de tuple.
\end{exo}

\begin{corrige}
\begin{listing}{}{03-15.py}\nathanliveProgWithoutText\end{listing}

\Par

Explications :

\begin{itemize}
\item \texttt{liste.sort()} commence part trier la liste dans l'ordre croissant; ainsi, la plus petite valeur de la liste sera \texttt{liste[0]} et la plus grande,\linebreak \texttt{liste[len(liste)-1]}. Il ne faut pas oublier que \texttt{len(liste)} donne le nombre d'items de la liste mais il y a un décalage d'index car on commence à l'index 0. Par exemple, pour une liste à 10 items, le dernier sera \texttt{liste[9]};

\item on calcule ensuite la somme des valeurs stockées dans la liste en définissant d'abord la variable \texttt{somme} à 0, puis en lui ajoutant toutes les valeurs avec la boucle \texttt{for i in liste}. La moyenne sera calculée en divisant \texttt{somme} par \texttt{len(liste)}.
\end{itemize}
\end{corrige}



\sectionnn{Dictionnaires}

%%% 16

\begin{exo}{Le Scrabble}{\null}{1}{5} 
Le Scrabble est une jeu de société où l'on doit former des mots avec un tirage aléatoire de lettres, chaque lettre valant un certain nombre de points.

Le tableau ci-dessous donne les points de certaines lettres :

\begin{center}
\begin{tabular}{|L|*{11}{Zc|}}
\hline
Lettres & A & B & C & D & E & F & G & H & I & J & K\\
\hline
Points & 1 & 3 & 3 & 2 & 1 & 4 & 2 & 4 & 1 & 8 & 5\\
\hline
\end{tabular}
\end{center}

\enlargethispage*{3em}

On considère le programme suivant :

\begin{listing}{}{03-16.py}\end{listing}

\begin{questions}
\item Quel est le type de la variable \texttt{scrabble}.
\item Expliquez l'affectation de cette variable.
\item Qu'affiche ce programme quand on entre le mot \og KAKI \fg{} au clavier?

\textit{On pourra s'aider d'un tableau d'exécution montrant chaque étape de la boucle.}
\item Quel est le rôle de ce programme ?
\end{questions}
\end{exo}

\begin{corrige}
\begin{questions}
\item La variable \texttt{scrabble} étant définie avec des accolades, et contenant des données de la forme \og A:~B \fg{} séparées par une virgule, elle est du type \textit{dictionnaire}.

\item La variable \texttt{scrabble} contient les lettres données dans le tableau de l'énoncé ainsi que les points associés à chacune des lettres.

\item La boucle \og \texttt{for i in mot} \fg{} signifie que l'on parcourt le mot entré au clavier. Rappelons que \texttt{scrabble.get(i)} donne la valeur attribuée à la variable \texttt{i} (donc ici, le nombre de points pour la lettre stockée dans \texttt{i}).

Le tableau suivant donne pas à pas les valeurs successives de la variable \texttt{somme} :

\begin{center}
\begin{tabular}{|L|*5{Zc|}}
\hline
Valeur de \texttt{i} & \cellcolor{gray} & K & A & K & I\\
\hline
Valeur de \texttt{scrabble.get(i)} & \cellcolor{gray} & 5 & 1 & 5 & 1\\
\hline
Valeur de \texttt{somme} & 0 & $5$ & $6$ & $11$ & $12$\\
\hline
\end{tabular}
\end{center}

\item À travers l'exemple précédent, on se rend compte que ce programme calcule le total des points d'un mot.
\end{questions}
\end{corrige}

%%% 17

\begin{exo}{Tableau physico-chimique}{\null}{1}{10} 
Le tableau suivant représente des informations physico-chimiques sur des éléments simples  : température d'ébullition ($T_e$) et de fusion ($T_f$), numéro (Z) et masse (M) atomique.

\begin{center}
\begin{tabular}{|C|*4{Zc|}}
\tabulartitle%\cline{2-5}
\multicolumn{1}{l|}{\cellcolor{white}} & $T_e$ & $T_f$ & Z & A \\
 \hline
Au & \numprint{2970} & \numprint{1063} & 79 & 196,967\\
\hline
Ga & \numprint{2237} & 29,8 & 31 & 69,72\\
\hline
\end{tabular}\psline(-4.88,0.92)(0,0.92)
\end{center}

Affectez les données de ce tableau à un dictionnaire \texttt{dico} Python de façon à pouvoir écrire par exemple :

\Par

\qquad\texttt{print(dico["Au"]["Z"])}\qquad (affiche : 79)
\end{exo}

\begin{corrige}
Il suffit de taper :

\begin{listing}{}{03-17.py}\end{listing}
\end{corrige}

%%% 18

\begin{exo}{Base de données}{\null}{2}{15} 
L'entreprise \textit{KiStokTout} possède une base de données dans laquelle elle enregistre les informations personnelles de ses clients :

\begin{center}
nom, prénom, adresse, âge, taille (en cm), poids (en kg).
\end{center}

Elle initialise cette base de données par la ligne suivante :

\Par

{\ttfamily
registre = [1,\{'nom':'HILUM' , 'prenom':'Mohan' ,\\
'adresse':'224 avenue des fleurs 75001 Paris', 'age':67,\\
'taille':178, 'poids':81\}]
}

\Par

où \og 1 \fg{} est  le numéro de ligne dans la base de données.

\begin{questions}
\item 
\begin{questions}
\item Quel est le type de la variable \texttt{registre} ?
\item Quel est le type de \texttt{registre[0]} ?
\item Quel est le type de \texttt{registre[1]} ?
\end{questions}

\item Que retourne l'instruction \texttt{registre[1]['nom']} ?\\
Quel est le type de \texttt{registre[1]['nom']} ? 
\newpage
\item D'après le cours, quelle instruction devrait-on utiliser pour ajouter les informations de Kévin Dupont, 24 ans, habitant au 5 allée des cailloux 33000 Bordeaux, mesurant 1m87 pour 95 kg, à la ligne 2 de la base  de données ?

\item Compléter le programme de la page suivante (compléter les points de suspension) afin qu'il permette à une personne d'entrer au clavier les informations tant qu'il y en a.

\begin{listing}{}{03-18-01.py}\end{listing}
\end{questions}
\end{exo}

\begin{corrige}
\begin{questions}
\item 
\begin{questions}
\item La variable \texttt{registre} étant définie par des crochets, elle est du type \textit{liste}.
\item La valeur \texttt{registre[0]} étant \og 1 \fg, son type est \textit{int}.
\item La valeur \texttt{registre[1]} est : \og \{'nom':'HILUM' , 'prenom':'Mohan' , 'adresse':'224 avenue des fleurs 75001 Paris', 'age':67, 'taille':178, 'poids':81\} \fg, donc son type est \textit{dictionnaire}.
\end{questions}

\item L'instruction \texttt{registre[1]['nom']} retourne : \og 'HILUM' \fg.

Le type de \texttt{registre[1]['nom']} est donc \textit{chaîne de caractères}.

\item D'après le cours, pour ajouter un item à une liste, il faut utiliser\linebreak l'instruction :

\Par

{\ttfamily
registre.extend([2,\{'nom':'DUPONT' , 'prenom':'Kévin' ,\\
'adresse':'5 allée des ponts 33000 Bordeaux', 'age':24,\\
'taille':187, 'poids':95\}])
}

\begin{attention}
L'énoncé précise bien que l'on doit utiliser une seule instruction, et non deux. Donc la méthode \texttt{append} ne peut pas fonctionner ici car elle ajouterait un item de type \textit{liste}, ce qui n'est pas souhaité.
\end{attention}

\newpage

\item \raisebox{-0.5\totalheight+3mm}{\begin{minipage}{\linewidth}\begin{listing}{}{03-18-02.py}\nathanliveProgWithoutText\end{listing}\end{minipage}}
\end{questions}
\end{corrige}


%%% 19

\begin{exo}{Création d'un dictionnaire}{\null}{3}{15} 
\'Ecrire une fonction \texttt{compte\_lettres} qui admet pour argument une chaîne de caractères et qui construit un dictionnaire contenant le nombre d'occurrences de tous les caractères utilisés dans la chaîne.

Le programme ressemblera à ceci :

\begin{listing}{}{03-19-01.py}\end{listing}

\Par

où \texttt{dico} est le dictionnaire attendu.
\end{exo}

\begin{corrige}
\begin{listing}{}{03-19-02.py}\nathanliveProgWithoutText\end{listing}

Explications : 

\begin{itemize}
\item on commence par définir la variable \texttt{dico} comme étant un dictionnaire (vide);

\item on parcourt ensuite la chaîne de caractères \texttt{chaine} avec la boucle \texttt{for i in chaine};

\item on teste avant tout si le caractère sur lequel on est (représenté par la variable \texttt{i}) figure dans le dictionnaire avec l'instruction \texttt{if i in dico}. Si tel est le cas, on incrémente le nombre attribué à cette lettre avec l'instruction \texttt{dico[i] = dico.get(i)+1};

\item sinon, on créé un item correspondant à cette lettre dans le dictionnaire et on lui attribue la valeur \og 1 \fg. 
\end{itemize}
\end{corrige}

%%% 20

\newpage
\begin{exo}{De l'hexadécimal au binaire}{\null}{3}{20} 
\'Ecrire un programme Python permettant de convertir un nombre hexadécimal en binaire à l'aide d'un dictionnaire.

\textit{Indication :} on pourra utiliser le programme de l'exercice \ref{algo-conversion-decimal-binaire} du chapitre \ref{chapitre-encodages}.
\end{exo}

\begin{corrige}
\enlargethispage*{3em}
\begin{listing}{}{03-20.py}\nathanliveProgWithoutText\end{listing}

\Par

Afin de rendre plus compréhensible le programme, deux fonctions ont été créées: \texttt{convertdecbin(n)} convertit le nombre n (exprimé en décimal) en binaire et retourne sous forme de chaîne de caractères le résultat (c'est la partie issue de l'exercice \ref{algo-conversion-decimal-binaire} du chapitre \ref{chapitre-encodages}). 

Ensuite, la fonction \texttt{converthexabin(n)} a été définie, qui convertit le nombre n (exprimé en décimal) en binaire et retourne le résultat sous la forme d'une chaîne de caractères. Dans cette fonction, on parcourt la variable \texttt{n} grâce à la boucle \texttt{for i in n:} et pour chaque caractère \texttt{i} rencontré, on commence d'abord par récupérer la clé correspondant à la valeur \texttt{i} dans le dictionnaire \texttt{dico}, puis on convertit cette valeur (qui est décimale) en binaire à l'aide de la fonction \texttt{convertdecbin}. Ensuite, on teste si la valeur \texttt{h} obtenue a une longueur de 4 bits; si tel n'est pas le cas (\texttt{if len(h)<4}), on complète par des \og 0 \fg{} afin que \texttt{h} ait une longueur de 4 bits. À la fin de ce test, une fois que l'on est assuré que \texttt{h} tient sur 4 bits, on concatène le résultat à la valeur de \texttt{hexa} précédente (\texttt{hexa += h}). Enfin, la variable \texttt{n} étant parcourue en entier, on retourne la valeur de la variable \texttt{hexa}, qui est la conversion demandée.
\end{corrige}

\sectionnn{Traitement de données en table}

%%% 21

\begin{exo}{Théorie des graphes}{\null}{1}{5} 
En théorie des graphes, une des branches des mathématiques, une matrice d'adjacence est une matrice ne contenant que des 0 et des 1. Nous la noterons $(a_{ij})$, où $a_{ij}$ représente le coefficient de la $i$-ième ligne et $j$-ième colonne, avec $i$ et $j$ deux entiers compris entre 1 et $n$.

Supposons que cette matrice soit représentée par la table \texttt{adj[i][j]}. On dit que les sommets $i$ et $j$ sont connectés si \texttt{adj[i][j]} est égal à 1.

\'Ecrire un code permettant d'afficher les sommets qui sont connectés.
\end{exo}

\begin{corrige}
On doit afficher toutes les instances de la valeur 1, comme dans le\linebreak paragraphe~\ref{afficher-instance} du cours.

On utilise alors le même modèle de code :

\begin{listing}{}{03-21.py}\end{listing}
\end{corrige}

%%% 22

\begin{exo}{Présence dans une base de données}{\null}{1}{5} 
Considérons une table \texttt{data} dans laquelle chaque ligne renferme des données sur les membres abonnés d'un site internet : nom, prénom, courriel, pseudonyme, mot de passe et d'autres informations diverses.

Lors de son enregistrement, l'abonné.e. est obligé.e. d'informer son courriel et son mot de passe, mais pas nécessairement son pseudo.

Pour s'identifier sur le site, une personne a besoin d'entrer son mot de passe ainsi que son pseudonyme.

\Par 

Une personne contacte l'administrateur du site et prétend qu'elle est abonnée et ne peut plus se connecter avec son pseudo \og BigArnaudDesMers \fg{} ni même avec son courriel \og bigarnaudofsea@gmail.com \fg.

\begin{questions}
\item \'Ecrire un code permettant à l'administrateur de voir rapidement si l'une des deux informations communiquées par la personne est présente dans la table.

\item Modifier ce code afin qu'il prenne en compte la casse des informations.
\end{questions}
\end{exo}

\begin{corrige}
\begin{questions}
\item Le code suivant permet d'afficher la phrase \og Informations présentes. \fg{} dans le cas où l'une des deux informations (pseudo ou courriel) est dans la table :

\begin{listing}{}{03-22-01.py}\end{listing}


\item Le pseudo peut comporter des majuscules et des minuscules. Il est donc intéressant de comparer les pseudos uniquement en minuscules.

Il y a deux possibilités.

\begin{itemize}
\item 1\iere{} possibilité : le pseudo et le courriel sont enregistrés en minuscules dans la table. Dans ce cas, une légère modification du code précédent est à apporter :

\begin{listing}{}{03-22-02.py}\end{listing}

\Par

\item 2\ieme{} possibilité : les pseudo et courriel sont enregistrés sans modification par rapport à la saisie initiale.

\Par
Dans ce cas, il faut parcourir tous les items et les convertir en minuscules, comme dans le programme page ci-contre.

\newpage

\begin{listing}{}{03-22-03.py}\end{listing}

\Par

Il est nécessaire d'utiliser un booléen afin de ne pas afficher plusieurs fois la phrase dans l'éventualité où le courriel et le pseudo figurent dans la table.
\end{itemize}

Dans le doute (comme aucune information n'est connue sur la table et la casse de ses items), il est préférable de choisir le second code. Mais quand on est administrateur d'un site internet, on pense à ce genre de choses et on enregistre les données au format le plus intéressant pour les manipulations futures.
\end{questions}
\end{corrige}

%%% 23
\newpage
\begin{exo}{Fichier INSEE}{\null}{1}{10} 
\nathanliveVideo
\label{video:exINSEE}
Sur le site Internet de l'INSEE, il est possible de télécharger des feuilles au format XLS (feuilles de calcul), qu'il est ensuite possible de convertir en fichier CSV.

Nous avons téléchargé une feuille nommée \og insee2018.xls \fg, et copié les 100 premières lignes qui m'intéressaient dans une nouvelle feuille afin de pouvoir la sauvegarder au format CSV. Nous avons au préalable changé le format des nombres afin de le rendre standard (le format initial des nombres, avec séparateur de milliers, n'est pas souhaitable).

\begin{questions}
\item \'Ecrire les lignes de code qui permettent d'importer les données de ce fichier dans une table nommée \texttt{data}.

\item Par défaut, les données étaient classées par ordre alphabétique sur le nom des régions, puis sur le nom des communes. 

\'Ecrire le code qui permet d'afficher toutes les communes, suivies de leur région et du nombre total d'habitants, dans l'ordre croissant de leur nombre total d'habitants (1 commune par ligne), tant que ce nombre total ne dépasse pas \numprint{1500}.

\item \'Ecrire le code permettant d'afficher les communes dont le nombre total d'habitants est strictement compris entre \numprint{2000} et \numprint{4000}.

\item En supposant que le fichier original n'ait pas été tronqué, écrire un code permettant d'afficher toutes les communes dont le nom commence par \og Pont- \fg, ainsi que leur région et le nombre total d'habitants.
\end{questions}
\end{exo}

\begin{corrige}
\begin{questions}
\item \rput(-1.1,0.1){\nathanliveVidWithoutText}Il est possible d'importer les données à l'aide des lignes suivantes :

\begin{listing}{}{03-23-01.py}\end{listing}

\begin{Remarque}
le fichier XLS initial comporte \numprint{3540} lignes de données, ce qui est bien trop pour Python (essayez et vous verrez que votre ordinateur va prendre très longtemps avant de finir l'importation). C'est pourquoi nous n'avons pris que 100 lignes lors de l'exportation en CSV.
\end{Remarque}

\item On trie d'abord selon la dernière colonne, puis on parcourt la table en affichant ce que l'on souhaite uniquement si la valeur de la dernière colonne est inférieure ou égale à \numprint{1500}.

\begin{listing}{}{03-23-02.py}\end{listing}

\Par

Il est important de retenir que les données importées sont au format texte; ainsi, quand on souhaite faire un test numérique sur une valeur, on doit convertir cette dernière en nombre en utilisant la fonction \texttt{int}.

\item Le code ressemble au précédent; seul le test change:

\begin{listing}{}{03-23-03.py}\end{listing}


\item Le code suivant permet d'afficher les communes dont le nom commence par \og Pont- \fg{} :

\begin{listing}{}{03-23-04.py}\end{listing}

\Par

On aurait aussi pu écrire en test : \texttt{if 'Pont-' in ligne[6]:}.
\end{questions}
\end{corrige}


%%% 24

%\begin{exo}{Les entiers dans d'une matrice}{\null}{2}{10}\'Ecrire un programme proposant à un.e. utilisateur.trice. de saisir un nombre entier $n$ tant que ce dernier n'est pas le carré d'un nombre entier et qui permet ensuite de construire la matrice :\[\begin{pmatrix}1 & 2  & \cdots & \sqrt{n}\\\sqrt{n+1} & \sqrt{n+2} & \cdots & 2\sqrt{n}\\\vdots & & \ddots & \vdots\\n-\sqrt{n}+1 & n-\sqrt{n}+2 & \cdots & n\end{pmatrix}\]Cette matrice est composée des nombres entiers de 1 à $n$ mis \og à la suite \fg.\end{exo}

%\begin{corrige}Avant tout, prenons un exemple pour comprendre cette matrice. Supposons que $n=16$. C'est bien un carré parfait (c'est-à-dire le carré d'un entier), et la matrice vaut alors :\[\begin{pmatrix}1&2&3&4\\5&6&7&8\\9&10&11&12\\13&14&15&16\end{pmatrix}\]Il s'agit bien ici de remplir la matrice avec les nombres entiers de 1 à $n$.Le programme se trouve page suivante.\ParExplications de la première partie (boucle \og while \fg):\begin{itemize}\item avant d'entrer dans la boucle, on créé un booléen \texttt{a} valant \textit{False} qui va nous servir d'indicateur pour savoir si le nombre entré est bien un carré parfait;\item on demande donc d'entrer un entier tant que ce booléen vaut \textit{False} (\texttt{while a == False});\item la variable \texttt{r} est la partie entière de la racine carrée de \texttt{n}. Le nombre stocké dans \texttt{n} est un carré parfait si le carré de \texttt{r} coïncide avec \texttt{n}. Par exemple, si $n=3$ alors $r=E\big(\sqrt3\big)=1$ (car $\sqrt3\approx1,732\ldots$); il est alors assuré qu'en calculant $r^2$, le résultat obtenu ne sera pas égal à 3. En revanche, si $n$ est un carré parfait alors il n'y aura pas d'erreur dans la représentation des résultats. Par exemple, si $n=4$, $r=E\big(\sqrt4\big)=2$, et $r^2=4=n$.Ainsi, le test \texttt{if r**2 == n} (si le carré de $r$ est égal à $n$) est légitime pour savoir si $n$ est un carré parfait. Et s'il est concluant alors le booléen prend la valeur \textit{True}.\end{itemize}\Par\nathanliveProgWithoutText\vspace*{-5mm}\begin{listing}{}{03-24.py}\end{listing}\ParExplications de la seconde partie :\begin{itemize}\item on commence par définir la matrice avec les bonnes dimensions en écrivant \texttt{matrice = [[0]*int(r) for i in range(int(r))]};\item on initialise ensuite une variable \texttt{c} à 0, variable qui va nous servir de compteur : comme chaque coefficient de la matrice est le précédent augmenté de~1, on va s'en servir pour calculer les coefficients à mettre dans la table qui représente la matrice;\item on parcourt ensuite chaque ligne (\texttt{for i in range(int(r))} : il est nécessaire d'écrire \og \texttt{int(r)} \fg{} car même si on sait que $r$ est entier, il est considéré comme un flottant car étant égal à une racine carrée;\item pour chaque ligne sur laquelle nous sommes, on parcourt chaque colonne (\texttt{for j in range(int(r))});\item on incrémente \texttt{c} (\texttt{c += 1}), qui nous donne la valeur du coefficient à mettre dans la table, à la position à laquelle nous sommes (\mbox{\texttt{matrice[i][j] = c}}).\end{itemize}\end{corrige}



\thumb
\AfficheCorrige
