2011-02-14 4 views
270

J'ai trouvé quelques réponses en ligne, mais je n'ai aucune expérience avec les expressions régulières, ce que je crois être ce qui est nécessaire ici.Python: Chaîne fractionnée avec plusieurs délimiteurs

J'ai une chaîne qui doit être séparée par ';' ou ',' Autrement dit, il doit s'agir d'un point-virgule ou d'une virgule suivi d'un espace. virgules individuelles sans espaces de fin doit être laissé intact

Exemple chaîne:

"b-staged divinylsiloxane-bis-benzocyclobutene [124221-30-3], mesitylene [000108-67-8]; polymerized 1,2-dihydro-2,2,4- trimethyl quinoline [026780-96-1]" 

devrait être divisé en une liste contenant les éléments suivants:

('b-staged divinylsiloxane-bis-benzocyclobutene [124221-30-3]' , 'mesitylene [000108-67-8]', 'polymerized 1,2-dihydro-2,2,4- trimethyl quinoline [026780-96-1]') 

Répondre

459

Heureusement, Python a cette intégré :)

import re 
re.split('; |, ',str) 

Mise à jour:
Suite à votre commentaire:

>>> a='Beautiful, is; better*than\nugly' 
>>> import re 
>>> re.split('; |, |\*|\n',a) 
['Beautiful', 'is', 'better', 'than', 'ugly'] 
+0

@Paul Il n'y en a pas. Vous ne comprenez pas correctement regex si vous pensez qu'il existe. Voir mon commentaire sur votre message ci-dessous. – alldayremix

+7

(Beau est mieux que) nugly ftw – TheIronKnuckle

+4

Je préfère l'écrire en tant que: re.split (r '; |, \ s', a) en remplaçant '' (caractère espace) par '\ s' (espace blanc) sauf si le caractère espace est une exigence stricte. –

103

Faites un str.replace('; ', ', ') puis un str.split(', ')

+6

+1; très spécifique et au point, pas générique. Ce qui est souvent mieux. –

+30

supposons que vous avez un 5 délimiteurs, vous devez traverser votre chaîne 5 fois –

+0

qui est très mauvais pour la performance –

19

Voici à quoi ressemble la regex:

import re 
# "semicolon or (a comma followed by a space)" 
pattern = re.compile(r";|, ") 

# "(semicolon or a comma) followed by a space" 
pattern = re.compile(r"[;,] ") 

print pattern.split(text) 
+0

merci, j'ai eu la bonne idée, je ne savais pas comment diviser les délimiteurs, maintenant je vois que vous utilisez le | symbole. – gt565k

59

est ici un moyen sûr pour tout itérables de délimiteurs, en utilisant régulièrement expressions:

>>> import re 
>>> delimiters = "a", "...", "(c)" 
>>> example = "stackoverflow (c) is awesome... isn't it?" 
>>> regexPattern = '|'.join(map(re.escape, delimiters)) 
>>> regexPattern 
'a|\\.\\.\\.|\\(c\\)' 
>>> re.split(regexPattern, example) 
['st', 'ckoverflow ', ' is ', 'wesome', " isn't it?"] 

re.escape permet de construire le motif automatiquement et d'avoir les délimiteurs échappés bien.

est ici cette solution en fonction pour votre plaisir du copier-coller:

def split(delimiters, string, maxsplit=0): 
    import re 
    regexPattern = '|'.join(map(re.escape, delimiters)) 
    return re.split(regexPattern, string, maxsplit) 

Si vous allez partager en utilisant souvent les mêmes délimiteurs, compiler votre expression régulière au préalable comme décrit et utiliser RegexObject.split.

+3

+1 est la solution la plus sûre et la plus extensible. – uhbif19

36

En réponse à la réponse de Jonathan ci-dessus, cela ne semble fonctionner que pour certains délimiteurs. Par exemple:

>>> a='Beautiful, is; better*than\nugly' 
>>> import re 
>>> re.split('; |, |\*|\n',a) 
['Beautiful', 'is', 'better', 'than', 'ugly'] 

>>> b='1999-05-03 10:37:00' 
>>> re.split('- :', b) 
['1999-05-03 10:37:00'] 

En mettant les délimiteurs entre crochets, cela semble fonctionner plus efficacement.

>>> re.split('[- :]', b) 
['1999', '05', '03', '10', '37', '00'] 
+7

Cela fonctionne pour tous les délimiteurs que vous spécifiez. Une regex de '-:' correspond exactement '-:' et ne divisera donc pas la chaîne date/heure. Une regex de '[-:]' correspond '' '' ',' ', ou ':' et divise ainsi la chaîne date/heure. Si vous voulez séparer seulement '-' et': 'alors votre regex devrait être' [-:] 'ou' - |: ', et si vous voulez séparer' -', '' et ': 'alors votre regex devrait être' [-:] 'ou' - | |: '. – alldayremix

+2

@alldayremix Je vois mon erreur: j'ai raté le fait que votre regex contient le OU | Je l'ai identifié aveuglément comme un séparateur désiré. – Paul

+0

Merci, j'avais besoin des supports pour mon cas d'utilisation. –

Questions connexes