Compte-rendu du T.P. 5 : ´ecriture binaire des entiers
1 Conversion de la base dix vers la base deux
1.1 En Python
b) bin renvoie une chaˆıne de caract`ere qui commence par 0b pour dire qu’elle repr´esente un
nombre en binaire.
c) Le programme suivant est long car comment´e mais sinon une ligne importe seule : la d´ef. de
m.
def bi n_ as_ in t ( n ):
" r en voie l ’ ´ec rit ure b in aire de n c omme un en tier "
m= int ( bin (n )[ 2:]) # on extrait dans la cha^ıne bin (n ) la partie qui com mence `a 2
# puis on convert it la cha^ıne en entier .
return m
d) Le shell r´epond 27. C’est donc une fa¸con imm´ediate de convertir de la base 2 `a la base 10.
N.B. Il ne s’agit pas juste d’un affichage !
1.2 En SciLab, avec petite initiation aux types en SciLab
d) On a compris que dec2bin(53) renvoie en fait une chaˆıne de caract`eres.
e) De la mˆeme fa¸con (en sens inverse), on a besoin de donner une chaˆıne comme argument de
la fonction bin2dec qui renvoie un nombre.
1.3 Test de vitesse en SciLab
En fait suivant la doc. de SciLab,timer() renvoie un temps C.P.U. qui n’est pas forc´ement en
seconde mais en nombre de cycles C.P.U. En fait, cela d´epend du syst`eme derri`ere. (Sous MacOS X
en fait, il semble que timer() donne bien des temps en seconde, ce qui explique que je ne m’´etais
pas m´efi´e.).
Donc il est pertinent pour comparer des programmes SciLab entre eux, mais pour comparer
avec Python. Suivant la doc. de SciLab, il semble pr´ef´erable pour avoir des temps en seconde,
d’utiliser tic() et toc() qui doivent donner des temps en seconde sur tous les syst`emes.
Chez moi le r´esultat est de toutes fa¸cons autour de 1,5 s.
1.4 Portage en Python et test de vitesse
Un avatar Python du programme pr´ec´edent est :
from time import clock
debut = clock ()
for i in range (1 ,100001): # d´ecalage de 1 n´ece ssair e par rapport `a Scilab
bin (i)
fin = clock ()
temps = clock () - debut # d iff ´erence entree le clock et le timer !
print ( temps )
Il donne un temps moyen de 0.028 s, beaucoup plus rapide ! A quoi bon utiliser SciLab alors ? On
va voir que SciLab sait faire beaucoup de choses... mais il n’est pas forc´ement optimis´e pour les
op´erations sur les entiers. Les built-in fonctions de Python sont rapides, ´ecrites en C.
1
1.5 Test de vitesse avec Numpy ?
a) Suivant votre installation, il connaˆıt ou pas ce module. Mais aujourd’hui avec Pyzo par
exemple, on peut avoir numpy sous Python 3.
Cette question permettait de voir ce qu’il en ´etait de votre installation !
b) Il est possible que votre installation ait numpy sous Python 2... et pas Python 3, ce `a quoi
il faudrait rem´edier.
c) Le programme est chez moi plus lent. En moyenne autour de 0.06, donc un peu plus de deux
fois plus lent. Donc Python 3 c’est mieux que Python 2.
d) L’aide dit que la fonction convertit aussi en binaire. Mais pour les n´egatifs, elle fait d’autres
choses : ´ecriture sous la forme d’un compl´ement `a deux. Nous y reviendrons.
e) C’est plus lent qu’avec bin. (D’un facteur dix par rapport `a Python 3 !). La raison d’ˆetre de
cette fonction semble vraiment ˆetre le cas des n´egatifs... Le code de la fonction est disponible
(comme pour toutes les fonctions numpy) sur :
https://github.com/numpy/numpy/blob/v1.7.0/numpy/core/numeric.py#L1720
On voit que cette fonction est coee en Python et que sa raison d’ˆetre est surtout ce qui se
passe avec les n´egatifs.
En revanche les built-in fonctions de Python sont coees en C et donc optimis´ees en
vitesse.
2 Impl´ementation des algorithmes
2.1 L’algo. scilab
La m´ethode est celle des poids faibles vers les poids forts d´ecrite en cours.
2.2 Le mˆeme algorithme ´ecrit en Python
def my_binary(n):
chaine=""
while (n>0):
a=n%2
chaine=str(a)+chaine # faire bien attention `a concatener du bon c^ot´e
n=(n-a)//2 # op´erateur de division entiere car n doit rester un entier.
return chaine
Le test de vitesse donne chez moi environ 1.05s.
N.B. : Cette algorithme a un d´efaut : si on prend 0 comme argument, il renvoie une chaˆıne
vide ! Une m´ethode pour le corriger est la suivante :
def m y_ bin ar y ( n ):
chaine=""
if n ==0:
return "0"
else:
while (n >0):
a =n %2
ch ai ne = str ( a )+ cha in e
n =( n - a )//2 # op´era teur de divisi on entiere
return chaine
2.3 L’algorithme avec les poids forts ´ecrit en Python
Premi`ere version : on en s’embarrasse pas, on trouve la longueur avec le log point de vue
plus math´ematique qu’informatique.
2
def poids_fort_bin(n):
#cr´eation d’une liste de d´epart avec la bonne longueur
from math import log
from math import floor
if n==0:
liste=[0]
else:
r=floor(log(n)/log(2))
liste=[1]+[0]*r
l=r+1 # la longueur de la liste
# on a cr´e une liste du bon format, on va continuer `a la remplir
n=n-2**r #
while n!=0:
r=floor(log(n)/log(2))
liste[l-1-r]=1
n=n-2**r
# `a ce stade on a cr´e une liste qui contient notre ´ecriture en base deux
# reste `a la convertir en cha^ıne de caract`eres.
chaine=""
for i in range(len(liste)):
chaine+=str(liste[i])
return chaine
Dans cet algo. (pas du tout optimal !) on passe par une liste car on peut la modifier ce qu’on pourrait
pas faire avec une chaˆıne. Le test de vitesse donne chez moi environ 2.2s. On s’y attendait.
2`eme version :
## Fonc ti on a uxi liaire perm ettant la plus grand puissance pgp de 2 in f´eri eure ou ´egale `a n
def p gp _2 ( n ):
" renvoie la plus grand puiss ance pgp de 2 inf´erieure ou ´egale `a n"
if n ==0:
return 0
else:
i =0
while 2** i <n :
i +=1
if 2** i == n :
return i
else :
return i-1
On peut alors appeler cette fonction dans notre code :
def p oi ds _f or t2 ( n ):
# c r´e at io n d ’ un e l is te au xi li ai re av ec la b on ne lo ng ue ur
if n ==0:
liste =[0]
else:
r= pgp_2 (n)
liste =[1] +[0]* r
l =r +1 # la longue ur de la liste
# on a cr´e´e une liste du bon format , on va co ntinu er `a la remplir
n=n -2** r #
while n !=0:
r= pgp_2 (n)
li st e [ l -1 - r ]= 1
3
n=n -2** r
# `a ce stade on a cr´e´e une liste qui conti ent notre ´ecriture en base deux
# reste `a la conve rtir en cha^ıne de car act `e res .
chaine=""
for i in range ( len ( liste )):
chaine += str ( liste [ i])
return chaine
4
1 / 4 100%
La catégorie de ce document est-elle correcte?
Merci pour votre participation!

Faire une suggestion

Avez-vous trouvé des erreurs dans linterface ou les textes ? Ou savez-vous comment améliorer linterface utilisateur de StudyLib ? Nhésitez pas à envoyer vos suggestions. Cest très important pour nous !