web-dev-qa-db-fra.com

Comment Python a-t-il implémenté la fonction intégrée pow ()?

Je dois écrire un programme pour calculer a**b % cb et c sont tous deux de très grands nombres. Si je viens d'utiliser a**b % c, c'est vraiment lent. Ensuite, j'ai découvert que la fonction intégrée pow() peut le faire très rapidement en appelant pow(a, b, c).
Je suis curieux de savoir comment Python l'implémente? Ou où pourrais-je trouver le fichier de code source qui implémente cette fonction?

42
wong2

Si a, b et c sont des entiers, l'implémentation peut être rendue plus efficace par exponentiation binaire et en réduisant modulo c à chaque étape, y compris la première (c'est-à-dire réduire a modulo c avant même de commencer). C’est ce que l’implémentation de long_pow() fait effectivement.

36
Sven Marnach

Vous pourriez envisager les deux implémentations suivantes pour calculer rapidement (x ** y) % z.

En Python:

def pow_mod(x, y, z):
    "Calculate (x ** y) % z efficiently."
    number = 1
    while y:
        if y & 1:
            number = number * x % z
        y >>= 1
        x = x * x % z
    return number

En C:

#include <stdio.h>

unsigned long pow_mod(unsigned short x, unsigned long y, unsigned short z)
{
    unsigned long number = 1;
    while (y)
    {
        if (y & 1)
            number = number * x % z;
        y >>= 1;
        x = (unsigned long)x * x % z;
    }
    return number;
}

int main()
{
    printf("%d\n", pow_mod(63437, 3935969939, 20628));
    return 0;
}
35
Noctis Skytower

Implémente pow (x, n) en Python

def myPow(x, n):
        p = 1
        if n<0:
            x = 1/x
            n = abs(n)

        # Exponentiation by Squaring

        while n:
            if n%2:
                p*= x
            x*=x
            n//=2
        return p

Implémente pow (x, n, m) en Python

def myPow(x,n,m):
            p = 1
            if n<0:
                x = 1/x
                n = abs(n)
            while n:
                if n%2:
                    p*= x%m
                x*=x%m
                n//=2
            return p

Commander ce link pour l'explication 

0
Akshay Nair

Python utilise les bibliothèques de mathématiques C pour les cas généraux et sa propre logique pour certains de ses concepts (tels que l'infini).

0
cmaynard

La ligne 1426 de ce fichier montre le code Python qui implémente math.pow, mais en gros, il se résume à appeler la bibliothèque standard C qui possède probablement une version hautement optimisée de cette fonction.

Python peut être assez lent pour les calculs intensifs, mais Psyco peut vous donner un coup de pouce assez rapide, mais il ne sera pas aussi bon que le code C appelant la bibliothèque standard.

0
Andrew Wilkinson

Je ne sais pas à propos de python, mais si vous avez besoin de pouvoirs rapides, vous pouvez utiliser l'exponentiation en quadrillant:

http://en.wikipedia.org/wiki/Exponentiation_by_squaring

C'est une méthode récursive simple qui utilise la propriété commutative des exposants.

0
Jonno_FTW