Algorithme CORDIC en python

Résolu
Longo_11 Messages postés 5 Date d'inscription   Statut Membre Dernière intervention   -  
Longo_11 Messages postés 5 Date d'inscription   Statut Membre Dernière intervention   -

Bonjour

Je suis tout nouveau sur le forum python. Je ne suis pas un spécialiste des langages évolués, je fais plutôt de l'assembleur. Voila pour la présentation .

Je travaille actuellement sur l'algorithme CORDIC pour le calcul sinus cosinus, et j’ai un petit problème avec le calcul suivant :

Aux = (x + ou - (Y >> k))

Je sais que sous python, les rotations droite ou gauche s'écrivent de la forme :

x >> 2

On va appliquer à x deux rotations à droite, mais dans algorithme, k vaut 0,6073. Bon même si ramène sous forme décimale, cela nous fait : y >> 6073 et c’est que je ne comprends pas.

Lien vers l'algorithme

Cordialement

A voir également:

5 réponses

mamiemando Messages postés 33746 Date d'inscription   Statut Modérateur Dernière intervention   7 871
 

Bonjour,

Préliminaires

Il y a deux problèmes dans le lien que tu pointes :

  • Il y a deux variables : K (en majuscule) est effectivement un flottant, et ce qui est noté k (en minuscule) qui est en réalité i.
  • On ne peut pas appliquer >> si l'opérande de gauche est u flottant, comme c'est le cas ici. En C/C++ on joue effectivement sur les décalages de bits pour accélérer les divisions par 2, mais c'est quelque chose que je déconseille très fortement sur un type non entier (la manière dont est encodé un flottant en mémoire est très différente). L'algorithme CORDIC proposé dans wikipedia confirme bien que l'auteur a bien voulu parler de divisions par des puissances de 2. Il faut donc changer ">> i" par "/ (2 ** i)".

Code proposé : en tenant compte des remarques faites en préliminaires :

#!/usr/bin/env python3

from math import atan, radians

def cordic(theta: float) -> tuple:
    """
    Approximates (cos(theta), sin(theta)) using the CORDIC algorithm.

    Args:
        theta (float): An angle, in radians.

    Returns:
        An approximation of (cos(theta), sin(theta)).
    """
    K = 0.6072529350088814
    n = 27
    atan_tab = [atan(2 ** (-i)) for i in range(0, n + 1)]

    x = K
    y = 0
    ecart = theta
    for i in range(0, n + 1):
        s = 1 if ecart >= 0 else -1
        aux = x - (s * y / (2 ** i))
        y += (s * (x / (2 ** i)))
        x = aux
        ecart -= s * atan_tab[i]
    return (x, y)

print(cordic(radians(30)))

(Depuis je l'ai rajouté dans la page wikipedia française dédiée)

Résultat : on retrouve bien un résultat conforme à celui qu'on peut simuler sur le site que tu pointes (ici pour 30°).

(0.8660254012499423, 0.5000000043898769)

Remarque : si tu es fan des décalages de bits, tu pourrais par contre remplacer le calcul (2 ** i) par :

def two_power_of_i(i):
    return (2 << (i - 1) if i >= 1 else 1)

for i in range(10):
    print(i, two_power_of_i(i))
0 1
1 2
2 4
3 8
4 16
5 32
6 64
7 128
8 256
9 512

Même si je ne te cache pas que personne n'écrirait ça en python :p D'ailleurs la plupart des gens se contenteraient de simplement utiliser math.sin ou math.cos.

Bonne chance

1
Diablo76 Messages postés 222 Date d'inscription   Statut Membre Dernière intervention   67
 

Salut,

Pour le calcul, c'est plutôt : 

num = int(input("Entrez un nombre: "))
rot = int(input("Entrez le nombre de rotation: "))

print(num >> rot)
0
Longo_11 Messages postés 5 Date d'inscription   Statut Membre Dernière intervention  
 

Merci pour ta réponse oui sur python c’est de la forme X >> rot  avec comme rot constante ou variable.

Cordialement 

0
Longo_11 Messages postés 5 Date d'inscription   Statut Membre Dernière intervention  
 

Bonsoir 

Merci pour vos réponses.J’ai terminé le programme en assembleur.

IL y a 10  passes et 5 chiffres décimaux et la précision est de 0,0137 pour le Sinus de 55 degrés’. cela prend 345781 cycles machine et occupe 200 octets de mémoire . Je vais mettre le code dans la section ASM.

Je ne sais pas comment faire pour marquer cela résolu.

Encore merci pour vos réponses 

Cordialement

0

Vous n’avez pas trouvé la réponse que vous recherchez ?

Posez votre question
Longo_11 Messages postés 5 Date d'inscription   Statut Membre Dernière intervention  
 

Bon je vois que c’est marqué résolu c’est super. Petit précision le micro contrôleur est un 8 bits un 18F de chez Microchip.

cordialement 

0