web-dev-qa-db-fra.com

Convertir une chaîne en binaire en python

J'ai besoin d'un moyen d'obtenir la représentation binaire d'une chaîne en python. par exemple. 

st = "hello world"
toBinary(st)

Existe-t-il un module sur un moyen astucieux de procéder?

68
user1090614

Quelque chose comme ça?

>>> st = "hello world"
>>> ' '.join(format(ord(x), 'b') for x in st)
'1101000 1100101 1101100 1101100 1101111 100000 1110111 1101111 1110010 1101100 1100100'

#using `bytearray`
>>> ' '.join(format(x, 'b') for x in bytearray(st))
'1101000 1100101 1101100 1101100 1101111 100000 1110111 1101111 1110010 1101100 1100100'
85
Ashwini Chaudhary

De manière plus pythonique, vous pouvez d’abord convertir votre chaîne en tableau d’octets, puis utiliser la fonction bin dans map:

>>> st = "hello world"
>>> map(bin,bytearray(st))
['0b1101000', '0b1100101', '0b1101100', '0b1101100', '0b1101111', '0b100000', '0b1110111', '0b1101111', '0b1110010', '0b1101100', '0b1100100']

Ou vous pouvez le rejoindre:

>>> ' '.join(map(bin,bytearray(st)))
'0b1101000 0b1100101 0b1101100 0b1101100 0b1101111 0b100000 0b1110111 0b1101111 0b1110010 0b1101100 0b1100100'

Notez que dans python3 vous devez spécifier un encodage pour la fonction bytearray:

>>> ' '.join(map(bin,bytearray(st,'utf8')))
'0b1101000 0b1100101 0b1101100 0b1101100 0b1101111 0b100000 0b1110111 0b1101111 0b1110010 0b1101100 0b1100100'

Vous pouvez également utiliser le module binascii dans Python 2:

>>> import binascii
>>> bin(int(binascii.hexlify(st),16))
'0b110100001100101011011000110110001101111001000000111011101101111011100100110110001100100'

hexlify renvoie la représentation hexadécimale des données binaires. Vous pouvez ensuite convertir en int en spécifiant 16 comme base puis la convertir en binaire avec bin.

34
Kasrâmvd

Vous pouvez accéder aux valeurs de code pour les caractères de votre chaîne à l'aide de la fonction intégrée ord(). Si vous devez ensuite formater ceci en binaire, la méthode string.format() fera le travail.

a = "test"
print(' '.join(format(ord(x), 'b') for x in a))

(Merci à Ashwini Chaudhary pour la publication de cet extrait de code.)

Bien que le code ci-dessus fonctionne dans Python 3, le problème devient plus compliqué si vous supposez un encodage autre que UTF-8. En Python 2, les chaînes sont des séquences d'octets et le codage ASCII est supposé par défaut. Dans Python 3, les chaînes sont supposées être au format Unicode et il existe un type bytes distinct qui agit davantage comme une chaîne Python 2. Si vous souhaitez utiliser un codage autre que UTF-8, vous devez le spécifier.

En Python 3, vous pouvez faire quelque chose comme ceci:

a = "test"
a_bytes = bytes(a, "ascii")
print(' '.join(["{0:b}".format(x) for x in a_bytes]))

Les différences entre le codage UTF-8 et le codage ascii ne seront pas évidentes pour les chaînes alphanumériques simples, mais deviendront importantes si vous traitez un texte comprenant des caractères ne faisant pas partie du jeu de caractères ascii.

15
Mark R. Wilkins

Nous avons juste besoin de l'encoder.

'string'.encode('ascii')
10
Tao

Ceci est une mise à jour des réponses existantes qui utilisaient bytearray() et ne peuvent plus fonctionner ainsi:

>>> st = "hello world"
>>> map(bin, bytearray(st))
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
TypeError: string argument without an encoding

Parce que, comme expliqué dans le lien ci-dessus, si la source est une chaîne, vous devez également indiquer le codage:

>>> map(bin, bytearray(st, encoding='utf-8'))
<map object at 0x7f14dfb1ff28>
1
Billal Begueradj

Dans Python version 3.6 et ultérieure, vous pouvez utiliser 'f-string' pour formater le résultat.

str = "hello world"
print(" ".join(f"{ord(i):08b}" for i in str))

01101000 01100101 01101100 01101100 01101111 00100000 01110111 01101111 01110010 01101100 01100100
  • Le côté gauche des deux points, ord (i), est l'objet réel dont la valeur sera formatée et insérée dans la sortie. Utiliser ord () vous donne le point de code base-10 pour un seul caractère str.

  • Le côté droit des deux-points est le spécificateur de format. 08 correspond à la largeur 8, le 0 est complété et le b sert de signe pour afficher le nombre obtenu en base 2 (binaire).

0
Vlad Bezden
def method_a(sample_string):
    binary = ' '.join(format(ord(x), 'b') for x in sample_string)

def method_b(sample_string):
    binary = ' '.join(map(bin,bytearray(sample_string,encoding='utf-8')))


if __== '__main__':

    from timeit import timeit

    sample_string = 'Convert this ascii strong to binary.'

    print(
        timeit(f'method_a("{sample_string}")',setup='from __main__ import method_a'),
        timeit(f'method_b("{sample_string}")',setup='from __main__ import method_b')
    )

# 9.564299999998184 2.943955828988692

method_b convertit beaucoup plus efficacement en tableau d'octets, car il appelle des fonctions de bas niveau au lieu de transformer manuellement chaque caractère en entier, puis de le convertir en valeur binaire.

0
Ben