web-dev-qa-db-fra.com

Expression régulière analysant un fichier binaire?

J'ai un fichier qui mélange des données binaires et des données texte. Je veux l'analyser à travers une expression régulière, mais j'obtiens cette erreur:

TypeError: can't use a string pattern on a bytes-like object

Je suppose que ce message signifie que Python ne veut pas analyser les fichiers binaires. J'ouvre le fichier avec le "rb" drapeaux.

Comment analyser des fichiers binaires avec des expressions régulières en Python?

EDIT: J'utilise Python 3.2.0

32
DonkeyMaster

Je pense que vous utilisez Python 3.

1.Ouvrir un fichier en mode binaire est simple mais subtil. La seule différence avec son ouverture en mode texte est que le paramètre mode contient un caractère 'b' .

........

Mais voici une différence: un objet flux binaire n'a pas d'attribut de codage. Cela a du sens, non? Vous lisez (ou écrivez) des octets , pas des chaînes, donc il n'y a pas de conversion pour Python à faire.

http://www.diveintopython3.net/files.html#read

Ensuite, dans Python 3, puisqu'un flux binaire à partir d'un fichier est un flux d'octets, un regex pour analyser un flux à partir d'un fichier doit être défini avec une séquence d'octets, pas une séquence de personnages.

Dans Python 2, une chaîne était un tableau d'octets dont l'encodage des caractères était suivi séparément. Si vous vouliez Python 2 pour garder une trace de l'encodage des caractères, vous a dû utiliser une chaîne Unicode (u '') à la place. Mais dans Python 3, une chaîne est toujours ce que Python 2 appelé chaîne Unicode - c'est , un tableau de caractères Unicode (de longueurs d'octets pouvant varier).

http://www.diveintopython3.net/case-study-porting-chardet-to-python-3.html

et

Dans Python 3, toutes les chaînes sont des séquences de caractères Unicode . Il n'y a rien de tel qu'une chaîne Python codée en UTF-8, ou une chaîne Python codée CP-1252). "Cette chaîne est-elle UTF-8?" Est une question non valide. UTF-8 est un moyen de coder des caractères sous la forme d'une séquence d'octets. Si vous souhaitez prendre une chaîne et la transformer en une séquence d'octets dans un codage de caractères particulier, Python 3 peut vous aider avec cela.

http://www.diveintopython3.net/strings.html#boring-stuff

et

4.6. Chaînes et octets # Les octets sont des octets; les personnages sont une abstraction. Une séquence immuable de caractères Unicode est appelée une chaîne. Une séquence immuable de nombres compris entre 0 et 255 est appelée un objet octets.

....

1. Pour définir un objet octets, utilisez la syntaxe b '' "littéral octet" . Chaque octet dans le littéral d'octet peut être un caractère ASCII ou un nombre hexadécimal codé de\x00 à\xff (0–255).

http://www.diveintopython3.net/strings.html#boring-stuff

Vous définissez donc votre expression régulière comme suit

pat = re.compile(b'[a-f]+\d+')

et pas comme

pat = re.compile('[a-f]+\d+')

Plus d'explications ici:

15.6.4. Impossible d'utiliser un modèle de chaîne sur un objet de type octets

27
eyquem

Dans votre re.compile vous devez utiliser un objet bytes, indiqué par un b initial:

r = re.compile(b"(This)")

C'est Python 3 étant pointilleux sur la différence entre les chaînes et les octets.

29
Scott Griffiths